diff --git a/src/actions/entries.js b/src/actions/entries.js index 899356e2..c8d3914a 100644 --- a/src/actions/entries.js +++ b/src/actions/entries.js @@ -181,16 +181,10 @@ export function loadEntry(entry, collection, slug) { const state = getState(); const backend = currentBackend(state.config); dispatch(entryLoading(collection, slug)); - let getPromise; - if (entry && entry.get('path') && entry.get('partial')) { - getPromise = backend.getEntry(entry.get('collection'), entry.get('slug'), entry.get('path')); - } else { - getPromise = backend.lookupEntry(collection, slug); - } - return getPromise - .then((loadedEntry) => { - return dispatch(entryLoaded(collection, loadedEntry)); - }); + return backend.getEntry(collection, slug) + .then(loadedEntry => ( + dispatch(entryLoaded(collection, loadedEntry)) + )); }; } diff --git a/src/backends/backend.js b/src/backends/backend.js index 17dd7ff0..edfe254f 100644 --- a/src/backends/backend.js +++ b/src/backends/backend.js @@ -86,8 +86,8 @@ class Backend { } // We have the file path. Fetch and parse the file. - getEntry(collection, slug, path) { - return this.implementation.getEntry(collection, slug, path) + getEntry(collection, slug) { + return this.implementation.getEntry(collection, slug, new Collection(collection).entryPath(slug)) .then(loadedEntry => this.entryWithFormat(collection, slug)(createEntry( collection.get('name'), slug, @@ -97,10 +97,6 @@ class Backend { ); } - lookupEntry(collection, slug) { - return this.getEntry(collection, slug, new Collection(collection).entryPath(slug)); - } - newEntry(collection) { return createEntry(collection.get('name')); } @@ -197,11 +193,11 @@ export function resolveBackend(config) { switch (name) { case 'test-repo': - return new Backend(new TestRepoBackend(config, slugFormatter), authStore); + return new Backend(new TestRepoBackend(config), authStore); case 'github': - return new Backend(new GitHubBackend(config, slugFormatter), authStore); + return new Backend(new GitHubBackend(config), authStore); case 'netlify-git': - return new Backend(new NetlifyGitBackend(config, slugFormatter), authStore); + return new Backend(new NetlifyGitBackend(config), authStore); default: throw new Error(`Backend not found: ${ name }`); } diff --git a/src/backends/github/implementation.js b/src/backends/github/implementation.js index 609ebf87..860a4c3e 100644 --- a/src/backends/github/implementation.js +++ b/src/backends/github/implementation.js @@ -32,7 +32,8 @@ export default class GitHub { } entriesByFolder(collection) { - return this.api.listFiles(collection.get('folder')).then(files => this.entriesByFiles(collection, files)); + return this.api.listFiles(collection.get('folder')) + .then(this.fetchFiles); } entriesByFiles(collection) { @@ -40,26 +41,25 @@ export default class GitHub { path: collectionFile.get('file'), label: collectionFile.get('label'), })); + return this.fetchFiles(files); + } + + fetchFiles = (files) => { const sem = semaphore(MAX_CONCURRENT_DOWNLOADS); const promises = []; files.forEach((file) => { - promises.push(new Promise((resolve, reject) => { - return sem.take(() => this.api.readFile(file.path, file.sha).then((data) => { - resolve( - { - file, - data, - } - ); + promises.push(new Promise((resolve, reject) => ( + sem.take(() => this.api.readFile(file.path, file.sha).then((data) => { + resolve({ file, data }); sem.leave(); }).catch((err) => { sem.leave(); reject(err); - })); - })); + })) + ))); }); return Promise.all(promises); - } + }; // Fetches a single entry. getEntry(collection, slug, path) { diff --git a/src/reducers/entries.js b/src/reducers/entries.js index 8e5b36ca..f29c0d90 100644 --- a/src/reducers/entries.js +++ b/src/reducers/entries.js @@ -31,7 +31,6 @@ const entries = (state = Map({ entities: Map(), pages: Map() }), action) => { collection = action.payload.collection; loadedEntries = action.payload.entries; page = action.payload.page; - return state.withMutations((map) => { loadedEntries.forEach(entry => ( map.setIn(['entities', `${ collection }.${ entry.slug }`], fromJS(entry).set('isFetching', false)) diff --git a/src/valueObjects/Collection.js b/src/valueObjects/Collection.js index 39f71025..58950a82 100644 --- a/src/valueObjects/Collection.js +++ b/src/valueObjects/Collection.js @@ -9,6 +9,26 @@ function formatToExtension(format) { }[format]; } +function slugFormatter(template, entryData) { + const date = new Date(); + const entry = (typeof entryData === 'string') ? entryData : entryData.get('title', entryData.get('path')); + const identifier = entry.match(/([^:\\/]*?)(?:\.([^ :\\/.]*))?$/)[1]; + return template.replace(/\{\{([^\}]+)\}\}/g, (_, name) => { + switch (name) { + case 'year': + return date.getFullYear(); + case 'month': + return (`0${ date.getMonth() + 1 }`).slice(-2); + case 'day': + return (`0${ date.getDate() }`).slice(-2); + case 'slug': + return identifier.trim().toLowerCase().replace(/[^a-z0-9\.\-_]+/gi, '-'); + default: + return identifier.trim().toLowerCase().replace(/[^a-z0-9\.\-_]+/gi, '-'); + } + }); +} + class FolderCollection { constructor(collection) { this.collection = collection; @@ -23,7 +43,7 @@ class FolderCollection { } entrySlug(path) { - return path.split('/').pop().replace(/\.[^\.]+$/, ''); + return slugFormatter(this.collection.get('slug'), path); } listMethod() {