[ARVADOS-WORKBENCH2] updated: 2.1.0-261-g23bafc0a
Git user
git at public.arvados.org
Fri Mar 19 22:41:02 UTC 2021
Summary of changes:
src/plugins/sample-tracker/batchList.tsx | 2 +-
src/plugins/sample-tracker/extraction.tsx | 43 +++--------
src/plugins/sample-tracker/patient.tsx | 4 +-
src/plugins/sample-tracker/sampleList.tsx | 124 ++++++++++++++++++++----------
4 files changed, 96 insertions(+), 77 deletions(-)
via 23bafc0aac6be3f60812258003dac77a00a4cc18 (commit)
from 7328f1f28fd792781e32c06232042a58186ea733 (commit)
Those revisions listed above that are new to this repository have
not appeared on any other notification email; so we list those
revisions in full, below.
commit 23bafc0aac6be3f60812258003dac77a00a4cc18
Author: Peter Amstutz <peter.amstutz at curii.com>
Date: Fri Mar 19 18:40:53 2021 -0400
Can edit extractions
Arvados-DCO-1.1-Signed-off-by: Peter Amstutz <peter.amstutz at curii.com>
diff --git a/src/plugins/sample-tracker/batchList.tsx b/src/plugins/sample-tracker/batchList.tsx
index 169583ee..77e7df91 100644
--- a/src/plugins/sample-tracker/batchList.tsx
+++ b/src/plugins/sample-tracker/batchList.tsx
@@ -28,7 +28,7 @@ import { getResource } from "~/store/resources/resources";
import { Typography } from '@material-ui/core';
import { initialize } from 'redux-form';
import { dialogActions } from "~/store/dialog/dialog-actions";
-import { AnalysisState } from './extraction';
+import { AnalysisState } from './sampleList';
import { StudyPathId } from './patient';
import { matchPath } from "react-router";
import { studyRoutePath } from './studyList';
diff --git a/src/plugins/sample-tracker/extraction.tsx b/src/plugins/sample-tracker/extraction.tsx
index 0335a2c1..4329ed83 100644
--- a/src/plugins/sample-tracker/extraction.tsx
+++ b/src/plugins/sample-tracker/extraction.tsx
@@ -8,7 +8,7 @@ import { WithDialogProps } from '~/store/dialog/with-dialog';
import { FormDialog } from '~/components/form-dialog/form-dialog';
import { ServiceRepository } from "~/services/services";
import { compose, Dispatch } from "redux";
-import { reduxForm, WrappedFieldProps, initialize, InjectedFormProps, Field, startSubmit, reset } from 'redux-form';
+import { reduxForm, WrappedFieldProps, InjectedFormProps, Field, startSubmit, reset } from 'redux-form';
import { RootState } from '~/store/store';
import { TextField } from "~/components/text-field/text-field";
import { getResource } from "~/store/resources/resources";
@@ -19,23 +19,13 @@ import { withStyles, WithStyles } from '@material-ui/core/styles';
import { LinkResource } from "~/models/link";
import { GroupClass, GroupResource } from "~/models/group";
import { withDialog } from "~/store/dialog/with-dialog";
-import { sampleTrackerExtractionType } from "./sampleList";
-
-const EXTRACTION_CREATE_FORM_NAME = "extractionCreateFormName";
+import { sampleTrackerExtractionType, EXTRACTION_CREATE_FORM_NAME, AnalysisState } from "./sampleList";
enum ExtractionType {
DNA = "DNA",
RNA = "RNA",
}
-export enum AnalysisState {
- NEW = "NEW",
- AT_SEQUENCING = "AT_SEQUENCING",
- SEQUENCED = "SEQUENCED",
- SEQ_FAILED = "SEQ_FAILED",
- ANALYSIS_COMPLETE = "ANALYSIS_COMPLETE"
-}
-
export interface ExtractionCreateFormDialogData {
sampleUuid: string;
extractionType: ExtractionType;
@@ -44,9 +34,10 @@ export interface ExtractionCreateFormDialogData {
sequencingCompleted: string;
state: AnalysisState;
batchUuid: string;
+ uuidSelf: string;
}
-type DialogExtractionProps = WithDialogProps<{}> & InjectedFormProps<ExtractionCreateFormDialogData>;
+type DialogExtractionProps = WithDialogProps<{ updating: boolean }> & InjectedFormProps<ExtractionCreateFormDialogData>;
type CssRules = 'selectWidth';
@@ -138,9 +129,9 @@ const ExtractionAddFields = () => <span>
const DialogExtractionCreate = (props: DialogExtractionProps) =>
<FormDialog
- dialogTitle='Add extraction'
+ dialogTitle={props.data.updating ? 'Edit sample' : 'Add sample'}
formFields={ExtractionAddFields}
- submitLabel='Add a extraction'
+ submitLabel={props.data.updating ? 'Update sample' : 'Add sample'}
{...props}
/>;
@@ -185,9 +176,11 @@ const createExtraction = (data: ExtractionCreateFormDialogData) =>
"sample_tracker:batch_uuid": "",
}
};
- // const newProject =
- await services.projectService.create(p);
-
+ if (data.uuidSelf) {
+ await services.projectService.update(data.uuidSelf, p);
+ } else {
+ await services.projectService.create(p);
+ }
dispatch(dialogActions.CLOSE_DIALOG({ id: EXTRACTION_CREATE_FORM_NAME }));
dispatch(reset(EXTRACTION_CREATE_FORM_NAME));
};
@@ -202,17 +195,3 @@ export const CreateExtractionDialog = compose(
}
})
)(DialogExtractionCreate);
-
-
-export const openExtractionCreateDialog = (sampleUuid: string) =>
- (dispatch: Dispatch, getState: () => RootState, services: ServiceRepository) => {
- dispatch(initialize(EXTRACTION_CREATE_FORM_NAME,
- {
- sampleUuid,
- additionalId: 1,
- state: AnalysisState.NEW
- }));
- dispatch(dialogActions.OPEN_DIALOG({
- id: EXTRACTION_CREATE_FORM_NAME, data: {}
- }));
- };
diff --git a/src/plugins/sample-tracker/patient.tsx b/src/plugins/sample-tracker/patient.tsx
index 4700c734..3525c891 100644
--- a/src/plugins/sample-tracker/patient.tsx
+++ b/src/plugins/sample-tracker/patient.tsx
@@ -13,7 +13,6 @@ import { DataTableDefaultView } from '~/components/data-table-default-view/data-
import { openContextMenu } from '~/store/context-menu/context-menu-actions';
import { ResourceKind } from '~/models/resource';
import { ContextMenuActionSet } from "~/views-components/context-menu/context-menu-action-set";
-import { openExtractionCreateDialog } from "./extraction";
import { InjectedFormProps, reduxForm, initialize } from 'redux-form';
import { WithDialogProps } from '~/store/dialog/with-dialog';
import { ProjectCreateFormDialogData } from '~/store/projects/project-create-actions';
@@ -29,7 +28,8 @@ import { ServiceRepository } from "~/services/services";
import { PATIENT_PANEL_CURRENT_UUID, sampleTrackerPatientType } from './patientList';
import {
SAMPLE_LIST_PANEL_ID, sampleListPanelActions,
- sampleBaseRoutePath, sampleListPanelColumns
+ sampleBaseRoutePath, sampleListPanelColumns,
+ openExtractionCreateDialog
} from './sampleList';
import { studyRoutePath } from './studyList';
diff --git a/src/plugins/sample-tracker/sampleList.tsx b/src/plugins/sample-tracker/sampleList.tsx
index a31a0b8d..f4e9991a 100644
--- a/src/plugins/sample-tracker/sampleList.tsx
+++ b/src/plugins/sample-tracker/sampleList.tsx
@@ -9,9 +9,12 @@ import { RootState } from '~/store/store';
import { DispatchProp, connect } from 'react-redux';
import { DataColumns } from '~/components/data-table/data-table';
import { createTree } from '~/models/tree';
-// import { ResourceName } from '~/views-components/data-explorer/renderers';
import { SortDirection } from '~/components/data-table/data-column';
import { bindDataExplorerActions } from "~/store/data-explorer/data-explorer-action";
+import { Typography } from '@material-ui/core';
+import { initialize } from 'redux-form';
+import { dialogActions } from "~/store/dialog/dialog-actions";
+import { Resource } from '~/models/resource';
import {
DataExplorerMiddlewareService,
@@ -38,8 +41,17 @@ export const SAMPLE_PANEL_CURRENT_UUID = "SamplePanelCurrentUUID";
export const sampleBaseRoutePath = "/SampleTracker/Sample";
export const sampleRoutePath = sampleBaseRoutePath + "/:uuid";
+export const EXTRACTION_CREATE_FORM_NAME = "extractionCreateFormName";
const PATIENT_PANEL_SAMPLES = "PATIENT_PANEL_SAMPLES";
+export enum AnalysisState {
+ NEW = "NEW",
+ AT_SEQUENCING = "AT_SEQUENCING",
+ SEQUENCED = "SEQUENCED",
+ SEQ_FAILED = "SEQ_FAILED",
+ ANALYSIS_COMPLETE = "ANALYSIS_COMPLETE"
+}
+
enum SamplePanelColumnNames {
NAME = "Name",
TIME_POINT = "Time point",
@@ -53,63 +65,95 @@ enum SamplePanelColumnNames {
BATCH_ID = "Batch",
}
-export const TimePointComponent = connect(
- (state: RootState, props: { uuid: string }) => {
- const resource = getResource<LinkResource>(props.uuid)(state.resources);
- return resource;
- })((resource: LinkResource & DispatchProp<any>) => <span>{resource.properties["sample_tracker:time_point"]}</span>);
-
-export const CollectionTypeComponent = connect(
- (state: RootState, props: { uuid: string }) => {
- const resource = getResource<LinkResource>(props.uuid)(state.resources);
- return resource;
- })((resource: LinkResource & DispatchProp<any>) => <span>{resource.properties["sample_tracker:collection_type"]}</span>);
-
-export const SampleTypeComponent = connect(
- (state: RootState, props: { uuid: string }) => {
- const resource = getResource<LinkResource>(props.uuid)(state.resources);
- return resource;
- })((resource: LinkResource & DispatchProp<any>) => <span>{resource.properties["sample_tracker:sample_type"]}</span>);
-
export const TimestampComponent = connect(
(state: RootState, props: { uuid: string, propertyname: string }) => {
const resource = getResource<LinkResource>(props.uuid)(state.resources);
return { resource, propertyname: props.propertyname };
})((props: { resource: LinkResource, propertyname: string } & DispatchProp<any>) => <span>{props.resource.properties[props.propertyname]}</span>);
-export const MultiCellComponent = connect(
- (state: RootState, props: { uuid: string, propertyname: string }) => {
+interface PropertiedResource extends Resource {
+ name: string;
+ properties: any;
+}
+
+export const openExtractionCreateDialog = (sampleUuid: string, editExisting?: PropertiedResource) =>
+ (dispatch: Dispatch, getState: () => RootState, services: ServiceRepository) => {
+ if (editExisting) {
+ dispatch(initialize(EXTRACTION_CREATE_FORM_NAME,
+ {
+ sampleUuid,
+ additionalId: editExisting.properties["sample_tracker:additional_id"],
+ state: editExisting.properties["sample_tracker:state"],
+ extractionType: editExisting.properties["sample_tracker:extraction_type"],
+ batchUuid: editExisting.properties["sample_tracker:batch_uuid"],
+ uuidSelf: editExisting.uuid,
+ }));
+ } else {
+ dispatch(initialize(EXTRACTION_CREATE_FORM_NAME,
+ {
+ sampleUuid,
+ additionalId: 1,
+ state: AnalysisState.NEW
+ }));
+ }
+ dispatch(dialogActions.OPEN_DIALOG({
+ id: EXTRACTION_CREATE_FORM_NAME, data: { updating: editExisting !== undefined, }
+ }));
+ };
+
+export const ExtractionComponent = connect((state: RootState, props: { resource: PropertiedResource }) => props)(
+ (props: { resource: PropertiedResource } & DispatchProp<any>) =>
+ <Typography color="primary" style={{ width: 'auto', cursor: 'pointer' }}
+ onClick={() => props.dispatch<any>(openExtractionCreateDialog(props.resource.properties["sample_tracker:sample_uuid"], props.resource))}
+ >{props.resource.name}</Typography>);
+
+
+export const PropertyComponent = (props: { resource: PropertiedResource, propertyname: string }) =>
+ <span>{props.resource.properties[props.propertyname]}</span>;
+
+export const ResourceComponent = connect(
+ (state: RootState, props: { uuid: string, render: (item: PropertiedResource) => React.ReactElement<any> }) => {
+ const resource = getResource<PropertiedResource>(props.uuid)(state.resources);
+ return { resource, render: props.render };
+ })((props: { resource: PropertiedResource, render: (item: PropertiedResource) => React.ReactElement<any> } & DispatchProp<any>) => props.render(props.resource));
+
+// {props.resource.properties["sample_tracker:sample_type"]}</span>);
+
+export const MultiResourceComponent = connect(
+ (state: RootState, props: { uuid: string, render: (item: PropertiedResource) => React.ReactElement<any> }) => {
const reverse = getProperty<{ [key: string]: any[] }>(PATIENT_PANEL_SAMPLES)(state.properties);
let items = (reverse && reverse[props.uuid]) || [];
items = items.map(item => {
const rsc = getResource<GroupResource>(item)(state.resources);
return rsc || { uuid: "", properties: {} };
});
- return { items, propertyname: props.propertyname };
- })((props: { items: any[], propertyname: string } & DispatchProp<any>) => <>
+ return { items, render: props.render };
+ })((props: { items: any[], render: (item: PropertiedResource) => React.ReactElement<any> } & DispatchProp<any>) => <>
{props.items.map(item =>
- <div key={item.uuid} > {item.properties[props.propertyname]}</div>
+ <div key={item.uuid} > {props.render(item)}</div>
)}
</>
);
export const sampleListPanelColumns: DataColumns<string> = [
- /*{
- name: SamplePanelColumnNames.NAME,
+ {
+ name: SamplePanelColumnNames.SAMPLE_TYPE,
selected: true,
configurable: true,
sortDirection: SortDirection.NONE,
filters: createTree(),
- render: uuid => <ResourceName uuid={uuid} />
- },*/
+ render: uuid => <ResourceComponent uuid={uuid}
+ render={rsc => <PropertyComponent resource={rsc} propertyname="sample_tracker:sample_type" />} />
+ },
{
name: SamplePanelColumnNames.TIME_POINT,
selected: true,
configurable: true,
sortDirection: SortDirection.NONE,
filters: createTree(),
- render: uuid => <TimePointComponent uuid={uuid} />
+ render: uuid => <ResourceComponent uuid={uuid}
+ render={rsc => <PropertyComponent resource={rsc} propertyname="sample_tracker:time_point" />} />
},
{
name: SamplePanelColumnNames.COLLECTED_AT,
@@ -120,20 +164,13 @@ export const sampleListPanelColumns: DataColumns<string> = [
render: uuid => <TimestampComponent uuid={uuid} propertyname="sample_tracker:collected_at" />
},
{
- name: SamplePanelColumnNames.COLLECTION_TYPE,
- selected: true,
- configurable: true,
- sortDirection: SortDirection.NONE,
- filters: createTree(),
- render: uuid => <CollectionTypeComponent uuid={uuid} />
- },
- {
- name: SamplePanelColumnNames.SAMPLE_TYPE,
+ name: SamplePanelColumnNames.NAME,
selected: true,
configurable: true,
sortDirection: SortDirection.NONE,
filters: createTree(),
- render: uuid => <SampleTypeComponent uuid={uuid} />
+ render: uuid => <ResourceComponent uuid={uuid}
+ render={rsc => <span>{rsc.name}</span>} />
},
{
name: SamplePanelColumnNames.FLOW_STARTED_AT,
@@ -157,7 +194,8 @@ export const sampleListPanelColumns: DataColumns<string> = [
configurable: true,
sortDirection: SortDirection.NONE,
filters: createTree(),
- render: uuid => <MultiCellComponent uuid={uuid.substr(sampleBaseRoutePath.length + 1)} propertyname="sample_tracker:extraction_type" />
+ render: uuid => <MultiResourceComponent uuid={uuid.substr(sampleBaseRoutePath.length + 1)}
+ render={rsc => <ExtractionComponent resource={rsc} />} />
},
{
name: SamplePanelColumnNames.BATCH_ID,
@@ -165,7 +203,8 @@ export const sampleListPanelColumns: DataColumns<string> = [
configurable: true,
sortDirection: SortDirection.NONE,
filters: createTree(),
- render: uuid => <MultiCellComponent uuid={uuid.substr(sampleBaseRoutePath.length + 1)} propertyname="sample_tracker:batch_uuid" />
+ render: uuid => <MultiResourceComponent uuid={uuid.substr(sampleBaseRoutePath.length + 1)}
+ render={rsc => <PropertyComponent resource={rsc} propertyname="sample_tracker:batch_uuid" />} />
},
{
name: SamplePanelColumnNames.TRACKER_STATE,
@@ -173,7 +212,8 @@ export const sampleListPanelColumns: DataColumns<string> = [
configurable: true,
sortDirection: SortDirection.NONE,
filters: createTree(),
- render: uuid => <MultiCellComponent uuid={uuid.substr(sampleBaseRoutePath.length + 1)} propertyname="sample_tracker:state" />
+ render: uuid => <MultiResourceComponent uuid={uuid.substr(sampleBaseRoutePath.length + 1)}
+ render={rsc => <PropertyComponent resource={rsc} propertyname="sample_tracker:state" />} />
}
];
-----------------------------------------------------------------------
hooks/post-receive
--
More information about the arvados-commits
mailing list