Skip to content

Commit

Permalink
removes english defaults, fixes locale switching bug
Browse files Browse the repository at this point in the history
  • Loading branch information
jhmullen committed Feb 7, 2019
1 parent 5c3873c commit 10a8cd2
Show file tree
Hide file tree
Showing 4 changed files with 55 additions and 45 deletions.
55 changes: 26 additions & 29 deletions packages/cms/src/components/cards/TextCard.jsx
Original file line number Diff line number Diff line change
Expand Up @@ -37,53 +37,50 @@ class TextCard extends Component {
}
}

populateLanguageContent(minData) {
const {locale, localeDefault, fields, plainfields} = this.props;
if (!minData.content.find(c => c.lang === locale)) {
const defCon = minData.content.find(c => c.lang === localeDefault);
const newCon = {id: minData.id, lang: locale};
if (defCon) {
Object.keys(defCon).forEach(k => {
if (k !== "id" && k !== "lang") newCon[k] = defCon[k];
});
}
// If for any reason the default was missing fields, fill the rest with blanks
fields.forEach(k => !newCon[k] ? newCon[k] = "" : null);
if (plainfields) plainfields.forEach(k => !newCon[k] ? newCon[k] = "" : null);
minData.content.push(newCon);
}
return minData;
}

hitDB() {
const {item, type, locale, localeDefault, fields, plainfields} = this.props;
const {item, type} = this.props;
const {id} = item;
axios.get(`/api/cms/${type}/get/${id}`).then(resp => {
// If this has been opened with a non default locale, and there is NO row for that locale,
// create a placeholder row that can be edited in the text boxes (and later saved)
const minData = resp.data;
if (!minData.content.find(c => c.lang === locale)) {
const def = minData.content.find(c => c.lang === localeDefault);
const newLangObj = {id: minData.id, lang: locale};
// If the default has had any portion filled in, pre-populate the placeholder with those.
if (def) {
Object.keys(def).forEach(k => {
if (k !== "id" && k !== "lang") newLangObj[k] = def[k];
});
}
// If for any reason the default was missing fields, fill the rest with blanks
fields.forEach(k => !newLangObj[k] ? newLangObj[k] = "" : null);
if (plainfields) plainfields.forEach(k => !newLangObj[k] ? newLangObj[k] = "" : null);
minData.content.push(newLangObj);
}
const minData = this.populateLanguageContent.bind(this)(resp.data);
this.setState({minData}, this.formatDisplay.bind(this));
});
}

formatDisplay() {
const {variables, selectors, locale, localeDefault, fields, plainfields} = this.props;
const {variables, selectors, locale} = this.props;
const {formatters} = this.context;
const {minData} = this.state;

const minData = this.populateLanguageContent.bind(this)(this.state.minData);
// Setting "selectors" here is pretty hacky. The varSwap needs selectors in order
// to run, and it expects them INSIDE the object. Find a better way to do this without
// polluting the object itself
minData.selectors = selectors;
// Swap vars, and extract the actual (multilingual) content
const content = varSwapRecursive(minData, formatters, variables).content;
const def = content.find(c => c.lang === localeDefault);
const currLang = content.find(c => c.lang === locale);
// Map over each of the default keys, and fetch its equivalent locale version (or default)
const displayData = {};
if (def) {
Object.keys(def).forEach(k => {
displayData[k] = currLang[k] ? currLang[k] : def[k];
});
}
// If for any reason the default was missing fields, fill the rest with blanks
fields.forEach(k => displayData[k] = currLang[k] ? currLang[k] : "");
if (plainfields) plainfields.forEach(k => displayData[k] = currLang[k] ? currLang[k] : "");
Object.keys(currLang).forEach(k => {
displayData[k] = currLang[k];
});
this.setState({displayData});
}

Expand Down
41 changes: 27 additions & 14 deletions packages/cms/src/profile/ProfileBuilder.jsx
Original file line number Diff line number Diff line change
Expand Up @@ -47,6 +47,14 @@ class ProfileBuilder extends Component {
});
}

componentDidUpdate(prevProps) {
if (prevProps.locale !== this.props.locale) {
const {currentSlug, currentNode} = this.state;
const id = currentNode ? currentNode.id : null;
if (currentSlug) this.fetchVariables.bind(this)(currentSlug, id, true);
}
}

/**
* Decode HTML elements such as &. Taken from:
* https://stackoverflow.com/questions/3700326/decode-amp-back-to-in-javascript
Expand All @@ -60,6 +68,7 @@ class ProfileBuilder extends Component {
buildNodes(openNode) {
const {profiles} = this.state;
const {stripHTML} = this.context.formatters;
const {localeDefault} = this.props;
const nodes = profiles.map(p => ({
id: `profile${p.id}`,
hasCaret: true,
Expand All @@ -69,8 +78,8 @@ class ProfileBuilder extends Component {
masterDimension: p.dimension,
data: p,
childNodes: p.topics.map(t => {
const enCon = t.content.find(c => c.lang === "en");
const title = enCon ? enCon.title : t.slug;
const defCon = t.content.find(c => c.lang === localeDefault);
const title = defCon && defCon.title ? defCon.title : t.slug;
return {
id: `topic${t.id}`,
hasCaret: false,
Expand Down Expand Up @@ -125,9 +134,10 @@ class ProfileBuilder extends Component {
addItem(n, dir) {
const {nodes} = this.state;
const {variablesHash, currentSlug} = this.state;
const {localeDefault} = this.props;
const {stripHTML} = this.context.formatters;
const {formatters} = this.context;
const variables = variablesHash[currentSlug] && variablesHash[currentSlug].en ? deepClone(variablesHash[currentSlug].en) : null;
const variables = variablesHash[currentSlug] && variablesHash[currentSlug][localeDefault] ? deepClone(variablesHash[currentSlug][localeDefault]) : null;
n = this.locateNode(n.itemType, n.data.id);
let parent;
let parentArray;
Expand Down Expand Up @@ -207,8 +217,8 @@ class ProfileBuilder extends Component {
if (topic.status === 200) {
obj.id = `topic${topic.data.id}`;
obj.data = topic.data;
const enCon = topic.data.content.find(c => c.lang === "en");
const title = enCon ? enCon.title : topic.slug;
const defCon = topic.data.content.find(c => c.lang === localeDefault);
const title = defCon && defCon.title ? defCon.title : topic.slug;
obj.label = varSwap(this.decode(stripHTML(title)), formatters, variables);
const parent = this.locateNode("profile", obj.data.profile_id);
parent.childNodes.push(obj);
Expand All @@ -231,8 +241,8 @@ class ProfileBuilder extends Component {
if (topic.status === 200) {
objTopic.id = `topic${topic.data.id}`;
objTopic.data = topic.data;
const enCon = topic.data.content.find(c => c.lang === "en");
const title = enCon ? enCon.title : topic.data.slug;
const defCon = topic.data.content.find(c => c.lang === localeDefault);
const title = defCon && defCon.title ? defCon.title : topic.data.slug;
objTopic.label = varSwap(this.decode(stripHTML(title)), formatters, variables);
const parent = this.locateNode("profile", obj.data.profile_id);
parent.childNodes.push(obj);
Expand All @@ -254,6 +264,7 @@ class ProfileBuilder extends Component {

deleteItem(n) {
const {nodes} = this.state;
const {localeDefault} = this.props;
const {stripHTML} = this.context.formatters;
// If this method is running, then the user has clicked "Confirm" in the Deletion Alert. Setting the state of
// nodeToDelete back to false will close the Alert popover.
Expand All @@ -264,8 +275,8 @@ class ProfileBuilder extends Component {
const parent = this.locateNode("profile", n.data.profile_id);
axios.delete("/api/cms/topic/delete", {params: {id: n.data.id}}).then(resp => {
const topics = resp.data.map(topicData => {
const enCon = topicData.content.find(c => c.lang === "en");
const title = enCon ? enCon.title : topicData.slug;
const defCon = topicData.content.find(c => c.lang === localeDefault);
const title = defCon && defCon.title ? defCon.title : topicData.slug;
return {
id: `topic${topicData.id}`,
hasCaret: false,
Expand Down Expand Up @@ -380,9 +391,10 @@ class ProfileBuilder extends Component {
reportSave(type, id, newValue) {
let {nodes} = this.state;
const {variablesHash, currentSlug} = this.state;
const {localeDefault} = this.props;
const {stripHTML} = this.context.formatters;
const {formatters} = this.context;
const variables = variablesHash[currentSlug] && variablesHash[currentSlug].en ? deepClone(variablesHash[currentSlug].en) : null;
const variables = variablesHash[currentSlug] && variablesHash[currentSlug][localeDefault] ? deepClone(variablesHash[currentSlug][localeDefault]) : null;
const node = this.locateNode.bind(this)(type, id);
// Update the label based on the new value. If this is a topic, this is the only thing needed
if (node) {
Expand Down Expand Up @@ -421,14 +433,15 @@ class ProfileBuilder extends Component {
*/
formatTreeVariables() {
const {variablesHash, currentSlug, nodes} = this.state;
const {localeDefault} = this.props;
const {stripHTML} = this.context.formatters;
const {formatters} = this.context;
const variables = variablesHash[currentSlug] && variablesHash[currentSlug].en ? deepClone(variablesHash[currentSlug].en) : null;
const variables = variablesHash[currentSlug] && variablesHash[currentSlug][localeDefault] ? deepClone(variablesHash[currentSlug][localeDefault]) : null;
const p = this.locateProfileNodeBySlug(currentSlug);
p.label = varSwap(p.data.slug, formatters, variables);
p.childNodes = p.childNodes.map(t => {
const enCon = t.data.content.find(c => c.lang === "en");
const title = enCon ? enCon.title : t.slug;
const defCon = t.data.content.find(c => c.lang === localeDefault);
const title = defCon && defCon.title ? defCon.title : t.slug;
t.label = varSwap(this.decode(stripHTML(title)), formatters, variables);
return t;
});
Expand All @@ -450,7 +463,7 @@ class ProfileBuilder extends Component {
if (callback) callback();
this.formatTreeVariables.bind(this)();
};
if (force || !variablesHash[slug]) {
if (force || !variablesHash[slug] || variablesHash[slug] && locale && !variablesHash[slug][locale]) {
if (id) {
axios.get(`/api/variables/${slug}/${id}?locale=${localeDefault}`).then(def => {
const defObj = {[localeDefault]: def.data};
Expand Down
2 changes: 1 addition & 1 deletion packages/cms/src/profile/ProfileEditor.jsx
Original file line number Diff line number Diff line change
Expand Up @@ -118,7 +118,7 @@ class ProfileEditor extends Component {
const {minData, recompiling} = this.state;
const {children, variables, preview, locale, localeDefault} = this.props;

if (!minData || !variables) return <Loading />;
if (!minData || !variables || variables && (!variables[localeDefault] || !variables[locale])) return <Loading />;

return (
<div className="cms-editor-inner">
Expand Down
2 changes: 1 addition & 1 deletion packages/cms/src/profile/TopicEditor.jsx
Original file line number Diff line number Diff line change
Expand Up @@ -120,7 +120,7 @@ class TopicEditor extends Component {
const {minData, recompiling} = this.state;
const {variables, preview, children, locale, localeDefault} = this.props;

if (!minData || !variables) return <Loading />;
if (!minData || !variables || variables && (!variables[localeDefault] || !variables[locale])) return <Loading />;

const varOptions = [<option key="always" value="always">Always</option>]
.concat(Object.keys(variables[localeDefault])
Expand Down

0 comments on commit 10a8cd2

Please sign in to comment.