fix: unify the title used in entry cards and workflow cards (#3573) (#3575)

This commit is contained in:
Hannes Küttner 2020-04-12 18:31:25 +02:00 committed by GitHub
parent 79b8469337
commit 625a9980f1
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
4 changed files with 85 additions and 14 deletions

View File

@ -5,9 +5,8 @@ import { boundGetAsset } from 'Actions/media';
import { Link } from 'react-router-dom';
import { colors, colorsRaw, components, lengths, zIndex } from 'netlify-cms-ui-default';
import { VIEW_STYLE_LIST, VIEW_STYLE_GRID } from 'Constants/collectionViews';
import { summaryFormatter } from 'Lib/formatters';
import { keyToPathArray } from 'Lib/stringTemplate';
import { selectIsLoadingAsset } from 'Reducers/medias';
import { selectEntryCollectionTitle } from 'Reducers/collections';
const ListCard = styled.li`
${components.card};
@ -122,15 +121,8 @@ const EntryCard = ({
const mapStateToProps = (state, ownProps) => {
const { entry, inferedFields, collection } = ownProps;
const label = entry.get('label');
const entryData = entry.get('data');
const defaultTitle =
label ||
(inferedFields.titleField && entryData.getIn(keyToPathArray(inferedFields.titleField)));
const summaryTemplate = collection.get('summary');
const summary = summaryTemplate
? summaryFormatter(summaryTemplate, entry, collection)
: defaultTitle;
const summary = selectEntryCollectionTitle(collection, entry);
let image = entryData.get(inferedFields.imageField);
if (image) {

View File

@ -9,6 +9,7 @@ import { colors, lengths } from 'netlify-cms-ui-default';
import { status } from 'Constants/publishModes';
import { DragSource, DropTarget, HTML5DragDrop } from 'UI';
import WorkflowCard from './WorkflowCard';
import { selectEntryCollectionTitle } from 'Reducers/collections';
const WorkflowListContainer = styled.div`
min-height: 60%;
@ -232,7 +233,7 @@ class WorkflowList extends React.Component {
<div>
<WorkflowCard
collectionLabel={collectionLabel || collectionName}
title={entry.get('label') || entry.getIn(['data', 'title'])}
title={selectEntryCollectionTitle(collection, entry)}
authorLastChange={entry.getIn(['metaData', 'user'])}
body={entry.getIn(['data', 'body'])}
isModification={isModification}

View File

@ -6,6 +6,7 @@ import collections, {
selectEntrySlug,
selectFieldsWithMediaFolders,
selectMediaFolders,
selectEntryCollectionTitle,
getFieldsNames,
selectField,
updateFieldByKey,
@ -383,6 +384,66 @@ describe('collections', () => {
});
});
describe('selectEntryCollectionTitle', () => {
const entry = fromJS({ data: { title: 'entry title', otherField: 'other field' } });
it('should return the entry title if set', () => {
const collection = fromJS({
fields: [{ name: 'title' }, { name: 'otherField' }],
});
expect(selectEntryCollectionTitle(collection, entry)).toEqual('entry title');
});
it('should return some other inferreable title if set', () => {
const headlineEntry = fromJS({
data: { headline: 'entry headline', otherField: 'other field' },
});
const collection = fromJS({
fields: [{ name: 'headline' }, { name: 'otherField' }],
});
expect(selectEntryCollectionTitle(collection, headlineEntry)).toEqual('entry headline');
});
it('should return the identifier_field content if defined in collection', () => {
const collection = fromJS({
identifier_field: 'otherField',
fields: [{ name: 'title' }, { name: 'otherField' }],
});
expect(selectEntryCollectionTitle(collection, entry)).toEqual('other field');
});
it('should return the entry label of a file collection', () => {
const labelEntry = fromJS({
slug: 'entry-name',
data: { title: 'entry title', otherField: 'other field' },
});
const collection = fromJS({
type: FILES,
files: [
{
name: 'entry-name',
label: 'entry label',
},
],
});
expect(selectEntryCollectionTitle(collection, labelEntry)).toEqual('entry label');
});
it('should return a formatted summary before everything else', () => {
const collection = fromJS({
summary: '{{title}} -- {{otherField}}',
identifier_field: 'otherField',
fields: [{ name: 'title' }, { name: 'otherField' }],
});
expect(selectEntryCollectionTitle(collection, entry)).toEqual('entry title -- other field');
});
});
describe('updateFieldByKey', () => {
it('should update field by key', () => {
const collection = fromJS({

View File

@ -15,6 +15,7 @@ import {
} from '../types/redux';
import { selectMediaFolder } from './entries';
import { keyToPathArray } from '../lib/stringTemplate';
import { summaryFormatter } from '../lib/formatters';
import { Backend } from '../backend';
const collections = (state = null, action: CollectionsAction) => {
@ -100,9 +101,8 @@ const selectors = {
return file && file.get('name');
},
entryLabel(collection: Collection, slug: string) {
const path = this.entryPath(collection, slug);
const files = collection.get('files');
return files && files.find(f => f?.get('file') === path).get('label');
const file = this.fileForEntry(collection, slug);
return file && file.get('label');
},
allowNewEntries() {
return false;
@ -352,6 +352,23 @@ export const selectInferedField = (collection: Collection, fieldName: string) =>
return null;
};
export const selectEntryCollectionTitle = (collection: Collection, entry: EntryMap) => {
// prefer formatted summary over everything else
const summaryTemplate = collection.get('summary');
if (summaryTemplate) return summaryFormatter(summaryTemplate, entry, collection);
// if the collection is a file collection return the label of the entry
if (collection.get('type') == FILES) {
const label = selectFileEntryLabel(collection, entry.get('slug'));
if (label) return label;
}
// try to infer a title field from the entry data
const entryData = entry.get('data');
const titleField = selectInferedField(collection, 'title');
return titleField && entryData.getIn(keyToPathArray(titleField));
};
export const COMMIT_AUTHOR = 'commit_author';
export const COMMIT_DATE = 'commit_date';