Skip to content

Commit

Permalink
deletedTags + layout
Browse files Browse the repository at this point in the history
  • Loading branch information
ericjeangirard committed Feb 23, 2024
1 parent 65ae26a commit e3f0b95
Show file tree
Hide file tree
Showing 8 changed files with 75 additions and 35 deletions.
15 changes: 12 additions & 3 deletions client/src/components/tag-input/index.jsx
Original file line number Diff line number Diff line change
Expand Up @@ -11,9 +11,11 @@ export default function TagInput({
onTagsChange,
placeholder,
tags,
deletedTags,
}) {
const [input, setInput] = useState('');
const [values, setValues] = useState(tags);
const [excludedValues, setExcludedValues] = useState(deletedTags);

const handleKeyDown = (e) => {
if ([9, 13].includes(e.keyCode) && input) {
Expand All @@ -25,7 +27,7 @@ export default function TagInput({
const newValues = [...values, { label: input.trim(), source: 'user' }];
setValues(newValues);
setInput('');
onTagsChange(newValues);
onTagsChange(newValues, excludedValues);
}
};

Expand All @@ -38,13 +40,18 @@ export default function TagInput({
}, [input, onInputHandler]);

const handleDeleteClick = (tag) => {
const deletedValues = excludedValues;
console.log('handleDeleteClick - deletedValues', deletedValues);
deletedValues.push(tag);
const newValues = [...values.filter((el) => el !== tag)];
// TODO this is buggy now, deleted tags should be memorized in the URL (searchParams)
setValues(newValues);
onTagsChange(newValues);
setExcludedValues(deletedValues);
console.log('deletedValues', deletedValues);
onTagsChange(newValues, deletedValues);
};

useEffect(() => setValues(tags), [tags]);
useEffect(() => setExcludedValues(deletedTags), [deletedTags]);

return (
<div>
Expand Down Expand Up @@ -95,6 +102,7 @@ TagInput.propTypes = {
onTagsChange: PropTypes.func.isRequired,
placeholder: PropTypes.string,
tags: PropTypes.arrayOf(PropTypes.object),
deletedTags: PropTypes.arrayOf(PropTypes.object),
};

TagInput.defaultProps = {
Expand All @@ -104,4 +112,5 @@ TagInput.defaultProps = {
onInputHandler: () => { },
placeholder: '',
tags: [],
deletedTags: [],
};
2 changes: 1 addition & 1 deletion client/src/pages/actions.jsx
Original file line number Diff line number Diff line change
Expand Up @@ -80,7 +80,7 @@ Actions.propTypes = {
worksNumber: PropTypes.number.isRequired,
})).isRequired,
allDatasets: PropTypes.arrayOf(PropTypes.shape({
affiliations: PropTypes.arrayOf(PropTypes.object).isRequired,
affiliations: PropTypes.arrayOf(PropTypes.object),
allIds: PropTypes.arrayOf(PropTypes.object).isRequired,
datasource: PropTypes.arrayOf(PropTypes.string).isRequired,
id: PropTypes.string.isRequired,
Expand Down
11 changes: 6 additions & 5 deletions client/src/pages/affiliationsView.jsx
Original file line number Diff line number Diff line change
Expand Up @@ -2,7 +2,7 @@ import { Column } from 'primereact/column';
import { DataTable } from 'primereact/datatable';
import PropTypes from 'prop-types';

import { nameTemplate, rorTemplate, statusTemplate } from '../utils/templates';
import { nameTemplate, rorTemplate, statusTemplate, worksExampleTemplate } from '../utils/templates';

export default function AffiliationsView({
allAffiliations,
Expand Down Expand Up @@ -33,10 +33,11 @@ export default function AffiliationsView({
value={allAffiliations}
>
<Column selectionMode="multiple" />
<Column field="status" header="Status" body={statusTemplate} />
<Column field="nameHtml" header="Affiliation" body={nameTemplate} sortable />
<Column field="rorHtml" header="RoR computed by OpenAlex" body={rorTemplate} sortable />
<Column field="worksNumber" header="Number of works" sortable />
<Column field="status" header="Status" body={statusTemplate} style={{ maxWidth: '150px' }} />
<Column field="nameHtml" header="Affiliation" body={nameTemplate} style={{ maxWidth: '250px' }} />
<Column field="rorHtml" header="RoR computed by OpenAlex" body={rorTemplate} style={{ maxWidth: '150px' }} />
<Column field="worksExamples" header="Examples of works" body={worksExampleTemplate} style={{ maxWidth: '200px' }} />
<Column field="worksNumber" header="Number of works" style={{ maxWidth: '100px' }} sortable />
</DataTable>
);
}
Expand Down
4 changes: 2 additions & 2 deletions client/src/pages/datasetsTab.jsx
Original file line number Diff line number Diff line change
Expand Up @@ -199,7 +199,7 @@ export default function DatasetsTab({ datasets, publishers, selectedDatasets, se

DatasetsTab.propTypes = {
datasets: PropTypes.arrayOf(PropTypes.shape({
affiliations: PropTypes.arrayOf(PropTypes.object).isRequired,
affiliations: PropTypes.arrayOf(PropTypes.object),
allIds: PropTypes.arrayOf(PropTypes.object).isRequired,
authors: PropTypes.arrayOf(PropTypes.string).isRequired,
datasource: PropTypes.arrayOf(PropTypes.string).isRequired,
Expand All @@ -210,7 +210,7 @@ DatasetsTab.propTypes = {
})).isRequired,
publishers: PropTypes.object.isRequired,
selectedDatasets: PropTypes.arrayOf(PropTypes.shape({
affiliations: PropTypes.arrayOf(PropTypes.object).isRequired,
affiliations: PropTypes.arrayOf(PropTypes.object),
allIds: PropTypes.arrayOf(PropTypes.object).isRequired,
authors: PropTypes.arrayOf(PropTypes.string).isRequired,
datasource: PropTypes.arrayOf(PropTypes.string).isRequired,
Expand Down
39 changes: 26 additions & 13 deletions client/src/pages/filters.jsx
Original file line number Diff line number Diff line change
Expand Up @@ -31,21 +31,25 @@ export default function Filters({ sendQuery }) {
if (searchParams.size === 0) {
setSearchParams({
affiliations: [],
deletedAffiliations: [],
datasets: false,
endYear: '2021',
startYear: '2021',
endYear: '2023',
startYear: '2023',
});
setTags([]);
} else {
setCurrentSearchParams({
affiliations: searchParams.getAll('affiliations'),
deletedAffiliations: searchParams.getAll('deletedAffiliations'),
datasets: searchParams.get('datasets') === 'true',
endYear: searchParams.get('endYear'),
startYear: searchParams.get('startYear'),
endYear: searchParams.get('endYear', '2023'),
startYear: searchParams.get('startYear', '2023'),
});
const affiliations = searchParams.getAll('affiliations');
const deletedAffiliations = searchParams.getAll('deletedAffiliations') || [];
const queries = affiliations.map((affiliation) => getRorData(affiliation));
const rorNames = await Promise.all(queries);
let rorNames = await Promise.all(queries);
rorNames = rorNames.filter((aff) => !deletedAffiliations.includes(aff));
const allTags = [];
const knownTags = {};
affiliations.forEach((affiliation) => {
Expand All @@ -58,14 +62,18 @@ export default function Filters({ sendQuery }) {
});
rorNames.flat().forEach((rorElt) => {
if (knownTags[rorElt.rorId.toLowerCase()] === undefined) {
allTags.push({ label: rorElt.rorId, source: 'ror', type: 'rorId' });
knownTags[rorElt.rorId.toLowerCase()] = 1;
if (!deletedAffiliations.includes(rorElt.rorId)) {
allTags.push({ label: rorElt.rorId, source: 'ror', type: 'rorId' });
knownTags[rorElt.rorId.toLowerCase()] = 1;
}
}
rorElt.names.forEach((rorName) => {
if (knownTags[rorName.toLowerCase()] === undefined) {
const isDangerous = rorName.length < 4;
allTags.push({ label: rorName, source: 'ror', type: 'affiliationString', rorId: rorElt.rorId, isDangerous });
knownTags[rorName.toLowerCase()] = 1;
if (!deletedAffiliations.includes(rorName)) {
const isDangerous = rorName.length < 4;
allTags.push({ label: rorName, source: 'ror', type: 'affiliationString', rorId: rorElt.rorId, isDangerous });
knownTags[rorName.toLowerCase()] = 1;
}
}
});
});
Expand All @@ -75,8 +83,13 @@ export default function Filters({ sendQuery }) {
getData();
}, [searchParams, setSearchParams]);

const onTagsChange = async (affiliations) => {
setSearchParams({ ...currentSearchParams, affiliations: affiliations.filter((affiliation) => affiliation.source === 'user').map((affiliation) => affiliation.label) });
const onTagsChange = async (affiliations, deletedAffiliations) => {
const previousDeleted = currentSearchParams.deletedAffiliations || [];
setSearchParams({
...currentSearchParams,
affiliations: affiliations.filter((affiliation) => affiliation.source === 'user').map((affiliation) => affiliation.label),
deletedAffiliations: deletedAffiliations.filter((affiliation) => affiliation.source !== 'user').map((affiliation) => affiliation.label).concat(previousDeleted),
});
};

const checkAndSendQuery = () => {
Expand Down Expand Up @@ -141,7 +154,7 @@ export default function Filters({ sendQuery }) {
<Col n="12">
<TagInput
hint="Press ENTER to search for several terms / expressions. If several, an OR operator is used."
label="Affiliation name"
label="Affiliation name, RoR identifier"
message={message}
messageType={messageType}
onTagsChange={onTagsChange}
Expand Down
16 changes: 8 additions & 8 deletions client/src/pages/index.jsx
Original file line number Diff line number Diff line change
Expand Up @@ -78,15 +78,15 @@ export default function Home() {
useEffect(() => {
if (data) {
// TODO do it on the API
const allDatasetsTmp = data.datasets.results
.map((dataset) => ({
const allDatasetsTmp = data.datasets?.results
?.map((dataset) => ({
...dataset,
affiliationsHtml: getAffiliationsHtmlField(dataset, regexp),
affiliationsTooltip: getAffiliationsTooltipField(dataset),
status: status.tobedecided.id,
}));
const allPublicationsTmp = data.publications.results
.map((publication) => ({
const allPublicationsTmp = data.publications?.results
?.map((publication) => ({
...publication,
affiliationsHtml: getAffiliationsHtmlField(publication, regexp),
affiliationsTooltip: getAffiliationsTooltipField(publication),
Expand Down Expand Up @@ -164,7 +164,7 @@ export default function Home() {
<PageSpinner />
</>
)}
{!isFetching && (allAffiliations.length > 0 || allDatasets.length > 0 || allPublications.length > 0) && (
{!isFetching && (allAffiliations?.length > 0 || allDatasets?.length > 0 || allPublications?.length > 0) && (
<Tabs defaultActiveTab={0}>
<Tab label="Grouped affiliations of works">
<AffiliationsTab
Expand All @@ -176,13 +176,13 @@ export default function Home() {
</Tab>
<Tab label="List all publications">
<PublicationsTab
publishers={data.publications.publishers}
publishers={data.publications?.publishers || []}
publications={allPublications}
selectedPublications={selectedPublications}
setSelectedPublications={setSelectedPublications}
tagPublications={tagPublications}
types={data.publications.types}
years={data.publications.years}
types={data.publications?.types || []}
years={data.publications?.years || []}
/>
</Tab>
<Tab label="List all datasets">
Expand Down
14 changes: 14 additions & 0 deletions client/src/utils/templates.jsx
Original file line number Diff line number Diff line change
Expand Up @@ -40,6 +40,19 @@ const linkedDOITemplate = (rowData) => {
return <span dangerouslySetInnerHTML={{ __html: html }} />;
};

//TODO: is there a way not to duplicate code : linkedDOITemplate and allIdsTemplate are the same but do not use the same field
const worksExampleTemplate = (rowData) => {
let html = '<ul>';
rowData.worksExample.filter((e) => ['doi', 'hal_id', 'crossref', 'datacite'].includes(e.id_type)).slice(0, 5).forEach((id) => {
html += `<li key="${id.id_value}">${id.id_type}:`;
const idLink = getIdLink(id.id_type, id.id_value);
html += idLink ? `<a target="_blank" href="${idLink}">${id.id_value}</a>` : `<span>${id.id_value}</span>`;
html += '</li>';
});
html += '</ul>';
return <span dangerouslySetInnerHTML={{ __html: html }} />;
};

const rorTemplate = (rowData) => {
let html = '<ul>';
rowData.rors.forEach((id) => {
Expand Down Expand Up @@ -116,4 +129,5 @@ export {
nameTemplate,
rorTemplate,
statusTemplate,
worksExampleTemplate
};
9 changes: 6 additions & 3 deletions server/src/utils/works.js
Original file line number Diff line number Diff line change
Expand Up @@ -283,6 +283,9 @@ const groupByAffiliations = ({ options, works }) => {
if (displayAffiliation.includes('</b>')) {
if (deduplicatedAffiliations?.[normalizedAffiliation]) {
deduplicatedAffiliations[normalizedAffiliation].works.push(id);
if (deduplicatedAffiliations[normalizedAffiliation].worksExample.length < 10) {
deduplicatedAffiliations[normalizedAffiliation].worksExample.push(work.allIds);
}
} else {
// eslint-disable-next-line no-param-reassign
deduplicatedAffiliations[normalizedAffiliation] = {
Expand All @@ -293,10 +296,8 @@ const groupByAffiliations = ({ options, works }) => {
key: affiliation.key,
status: 'tobedecided',
works: [id],
worksExample: [work.allIds],
};
if (affiliation.key.includes('essec business school cergy [ source: OpenAlex ]')) {
console.log('ttttt', affiliation.key);
}
}
}
}
Expand All @@ -306,10 +307,12 @@ const groupByAffiliations = ({ options, works }) => {
allAffiliationsTmp = Object.values(allAffiliationsTmp)
.map((affiliation, index) => {
const uniqueWorks = [...new Set(affiliation.works)];
const uniqueWorksExample = [...new Set(affiliation.worksExample.flat())];
return ({
...affiliation,
id: index.toString(),
works: uniqueWorks,
worksExample: uniqueWorksExample,
worksNumber: uniqueWorks.length,
});
});
Expand Down

0 comments on commit e3f0b95

Please sign in to comment.