diff --git a/bigbluebutton-html5/.gitignore b/bigbluebutton-html5/.gitignore
index 3a833eaf4f800bfece09c1cd77ed8cd112714fc2..b8bd4a6520ec7750e5c0d810ffc70d79e9e3e98a 100755
--- a/bigbluebutton-html5/.gitignore
+++ b/bigbluebutton-html5/.gitignore
@@ -3,5 +3,7 @@ npm-debug.log
 node_modules/
 .meteor/dev_bundle
 tests/webdriverio/.testing-env
+public/locales/de_DE.json
+public/locales/ja_JP.json
 
 
diff --git a/bigbluebutton-html5/imports/startup/client/intl.jsx b/bigbluebutton-html5/imports/startup/client/intl.jsx
index 0d44ca2d67522c69ce2c6bcefdf016f449523f8f..c56fac96baa696728478bc9e458028b0b98e5016 100644
--- a/bigbluebutton-html5/imports/startup/client/intl.jsx
+++ b/bigbluebutton-html5/imports/startup/client/intl.jsx
@@ -63,6 +63,7 @@ class IntlStartup extends Component {
 
   fetchLocalizedMessages(locale, init = false) {
     const url = `./locale?locale=${locale}&init=${init}`;
+    const localesPath = 'locales';
 
     this.setState({ fetching: true }, () => {
       fetch(url)
@@ -73,11 +74,65 @@ class IntlStartup extends Component {
 
           return response.json();
         })
-        .then(({ messages, normalizedLocale }) => {
-          const dasherizedLocale = normalizedLocale.replace('_', '-');
-          this.setState({ messages, fetching: false, normalizedLocale: dasherizedLocale }, () => {
-            IntlStartup.saveLocale(dasherizedLocale);
-          });
+        .then(({ normalizedLocale, regionDefaultLocale }) => {
+          fetch(`${localesPath}/${DEFAULT_LANGUAGE}.json`)
+            .then((response) => {
+              if (!response.ok) {
+                return Promise.reject();
+              }
+              return response.json();
+            })
+            .then((messages) => {
+              if (regionDefaultLocale !== '') {
+                fetch(`${localesPath}/${regionDefaultLocale}.json`)
+                  .then((response) => {
+                    if (!response.ok) {
+                      return Promise.resolve();
+                    }
+                    return response.json();
+                  })
+                  .then((regionDefaultMessages) => {
+                    messages = Object.assign(messages, regionDefaultMessages);
+                    return messages;
+                  });
+              }
+
+              if (normalizedLocale !== DEFAULT_LANGUAGE && normalizedLocale !== regionDefaultLocale) {
+                fetch(`${localesPath}/${normalizedLocale}.json`)
+                  .then((response) => {
+                    if (!response.ok) {
+                      return Promise.reject();
+                    }
+                    return response.json();
+                  })
+                  .then((localeMessages) => {
+                    messages = Object.assign(messages, localeMessages);
+                    return messages;
+                  })
+                  .catch(() => {
+                    normalizedLocale = (regionDefaultLocale) || DEFAULT_LANGUAGE;
+                    const dasherizedLocale = normalizedLocale.replace('_', '-');
+                    this.setState({ messages, fetching: false, normalizedLocale: dasherizedLocale }, () => {
+                      IntlStartup.saveLocale(normalizedLocale);
+                    });
+                  });
+              }
+
+              return messages;
+            })
+            .then((messages) => {
+              const dasherizedLocale = normalizedLocale.replace('_', '-');
+              this.setState({ messages, fetching: false, normalizedLocale: dasherizedLocale }, () => {
+                IntlStartup.saveLocale(dasherizedLocale);
+              });
+            })
+            .catch(() => {
+              normalizedLocale = DEFAULT_LANGUAGE;
+              const dasherizedLocale = normalizedLocale.replace('_', '-');
+              this.setState({ fetching: false, normalizedLocale: dasherizedLocale }, () => {
+                IntlStartup.saveLocale(normalizedLocale);
+              });
+            });
         })
         .catch(() => {
           this.setState({ fetching: false, normalizedLocale: null }, () => {
diff --git a/bigbluebutton-html5/imports/startup/server/index.js b/bigbluebutton-html5/imports/startup/server/index.js
index 9be2dd4163eb79d2494f2ca04bc589a6bb29af15..5f6508e6a32a1c6ac6d7cf89defff9dae9f2a45d 100755
--- a/bigbluebutton-html5/imports/startup/server/index.js
+++ b/bigbluebutton-html5/imports/startup/server/index.js
@@ -12,7 +12,16 @@ import Redis from './redis';
 import setMinBrowserVersions from './minBrowserVersion';
 
 let guestWaitHtml = '';
-const AVAILABLE_LOCALES = fs.readdirSync('assets/app/locales');
+
+const env = Meteor.isDevelopment ? 'development' : 'production';
+
+const meteorRoot = fs.realpathSync(`${process.cwd()}/../`);
+
+const applicationRoot = (env === 'development')
+  ? fs.realpathSync(`${meteorRoot}'/../../../../public/locales/`)
+  : fs.realpathSync(`${meteorRoot}/../programs/web.browser/app/locales/`);
+
+const AVAILABLE_LOCALES = fs.readdirSync(`${applicationRoot}`);
 const FALLBACK_LOCALES = JSON.parse(Assets.getText('config/fallbackLocales.json'));
 
 process.on('uncaughtException', (err) => {
@@ -27,7 +36,6 @@ process.on('uncaughtException', (err) => {
 
 Meteor.startup(() => {
   const APP_CONFIG = Meteor.settings.public.app;
-  const env = Meteor.isDevelopment ? 'development' : 'production';
   const CDN_URL = APP_CONFIG.cdn;
   const instanceId = parseInt(process.env.INSTANCE_ID, 10) || 1;
 
@@ -191,7 +199,7 @@ WebApp.connectHandlers.use('/locale', (req, res) => {
   const browserLocale = override && req.query.init === 'true'
     ? override.split(/[-_]/g) : req.query.locale.split(/[-_]/g);
 
-  const localeList = [fallback];
+  let localeFile = fallback;
 
   const usableLocales = AVAILABLE_LOCALES
     .map(file => file.replace('.json', ''))
@@ -199,35 +207,29 @@ WebApp.connectHandlers.use('/locale', (req, res) => {
       ? [...locales, locale]
       : locales), []);
 
-  const regionDefault = usableLocales.find(locale => browserLocale[0] === locale);
-
-  if (regionDefault) localeList.push(regionDefault);
-  if (!regionDefault && usableLocales.length) localeList.push(usableLocales[0]);
-
   let normalizedLocale;
-  let messages = {};
 
   if (browserLocale.length > 1) {
     normalizedLocale = `${browserLocale[0]}_${browserLocale[1].toUpperCase()}`;
-    localeList.push(normalizedLocale);
+
+    const normDefault = usableLocales.find(locale => normalizedLocale === locale);
+    if (normDefault) localeFile = normDefault;
   }
 
-  localeList.forEach((locale) => {
-    try {
-      const data = Assets.getText(`locales/${locale}.json`);
-      messages = Object.assign(messages, JSON.parse(data));
-      normalizedLocale = locale;
-    } catch (e) {
-      Logger.info(`'Could not process locale ${locale}:${e}`);
-      // Getting here means the locale is not available in the current locale files.
-    }
-  });
+  const regionDefault = usableLocales.find(locale => browserLocale[0] === locale);
+
+  if (localeFile === fallback && regionDefault !== localeFile) {
+    localeFile = regionDefault;
+  }
 
   res.setHeader('Content-Type', 'application/json');
-  res.end(JSON.stringify({ normalizedLocale, messages }));
+  res.end(JSON.stringify({
+    normalizedLocale: localeFile,
+    regionDefaultLocale: (regionDefault && regionDefault !== localeFile) ? regionDefault : '',
+  }));
 });
 
-WebApp.connectHandlers.use('/locales', (req, res) => {
+WebApp.connectHandlers.use('/locale-list', (req, res) => {
   if (!avaibleLocalesNamesJSON) {
     avaibleLocalesNamesJSON = JSON.stringify(generateLocaleOptions());
   }
diff --git a/bigbluebutton-html5/imports/ui/components/legacy/component.jsx b/bigbluebutton-html5/imports/ui/components/legacy/component.jsx
index f6c049f3452dc5cc425822c770f4ba119e834c2d..b859270bd6d4c88bf16b98e5fec0126d5cf2b665 100755
--- a/bigbluebutton-html5/imports/ui/components/legacy/component.jsx
+++ b/bigbluebutton-html5/imports/ui/components/legacy/component.jsx
@@ -69,16 +69,17 @@ const FETCHING = 'fetching';
 const FALLBACK = 'fallback';
 const READY = 'ready';
 const supportedBrowsers = ['chrome', 'firefox', 'safari', 'opera', 'edge', 'yandex'];
+const DEFAULT_LANGUAGE = Meteor.settings.public.app.defaultSettings.application.fallbackLocale;
 
 export default class Legacy extends Component {
   constructor(props) {
     super(props);
 
     const locale = navigator.languages ? navigator.languages[0] : false
-      || navigator.language
-      || Meteor.settings.public.app.defaultSettings.application.fallbackLocale;
+      || navigator.language;
 
     const url = `./locale?locale=${locale}`;
+    const localesPath = 'locales';
 
     const that = this;
     this.state = { viewState: FETCHING };
@@ -90,9 +91,56 @@ export default class Legacy extends Component {
 
         return response.json();
       })
-      .then(({ messages, normalizedLocale }) => {
-        const dasherizedLocale = normalizedLocale.replace('_', '-');
-        that.setState({ messages, normalizedLocale: dasherizedLocale, viewState: READY });
+      .then(({ normalizedLocale, regionDefaultLocale }) => {
+        fetch(`${localesPath}/${DEFAULT_LANGUAGE}.json`)
+          .then((response) => {
+            if (!response.ok) {
+              return Promise.reject();
+            }
+            return response.json();
+          })
+          .then((messages) => {
+            if (regionDefaultLocale !== '') {
+              fetch(`${localesPath}/${regionDefaultLocale}.json`)
+                .then((response) => {
+                  if (!response.ok) {
+                    return Promise.resolve();
+                  }
+                  return response.json();
+                })
+                .then((regionDefaultMessages) => {
+                  messages = Object.assign(messages, regionDefaultMessages);
+                  this.setState({ messages});
+                });
+            }
+
+            if (normalizedLocale && normalizedLocale !== DEFAULT_LANGUAGE && normalizedLocale !== regionDefaultLocale) {
+              fetch(`${localesPath}/${normalizedLocale}.json`)
+                .then((response) => {
+                  if (!response.ok) {
+                    return Promise.reject();
+                  }
+                  return response.json();
+                })
+                .then((localeMessages) => {
+                  messages = Object.assign(messages, localeMessages);
+                  this.setState({ messages});
+                })
+                .catch(() => {
+                  normalizedLocale = (regionDefaultLocale) || DEFAULT_LANGUAGE;
+                  const dasherizedLocale = normalizedLocale.replace('_', '-');
+                  this.setState({ messages, normalizedLocale: dasherizedLocale, viewState: READY });
+                });
+            }
+            return messages;
+          })
+          .then((messages) => {
+            const dasherizedLocale = normalizedLocale.replace('_', '-');
+            this.setState({ messages, normalizedLocale: dasherizedLocale, viewState: READY });
+          })
+          .catch(() => {
+            that.setState({ viewState: FALLBACK });
+          });
       })
       .catch(() => {
         that.setState({ viewState: FALLBACK });
diff --git a/bigbluebutton-html5/imports/ui/components/settings/service.js b/bigbluebutton-html5/imports/ui/components/settings/service.js
index 85af45dddd425ef6af2f48f04cd3115870e57262..42698cb30c268933700445e9841c7c8ee30ad0a4 100644
--- a/bigbluebutton-html5/imports/ui/components/settings/service.js
+++ b/bigbluebutton-html5/imports/ui/components/settings/service.js
@@ -27,7 +27,7 @@ const updateSettings = (obj, msg) => {
   }
 };
 
-const getAvailableLocales = () => fetch('./locales').then(locales => locales.json());
+const getAvailableLocales = () => fetch('./locale-list').then(locales => locales.json());
 
 export {
   getUserRoles,
diff --git a/bigbluebutton-html5/private/locales/ar.json b/bigbluebutton-html5/public/locales/ar.json
similarity index 100%
rename from bigbluebutton-html5/private/locales/ar.json
rename to bigbluebutton-html5/public/locales/ar.json
diff --git a/bigbluebutton-html5/private/locales/az.json b/bigbluebutton-html5/public/locales/az.json
similarity index 100%
rename from bigbluebutton-html5/private/locales/az.json
rename to bigbluebutton-html5/public/locales/az.json
diff --git a/bigbluebutton-html5/private/locales/bg_BG.json b/bigbluebutton-html5/public/locales/bg_BG.json
similarity index 100%
rename from bigbluebutton-html5/private/locales/bg_BG.json
rename to bigbluebutton-html5/public/locales/bg_BG.json
diff --git a/bigbluebutton-html5/private/locales/ca.json b/bigbluebutton-html5/public/locales/ca.json
similarity index 100%
rename from bigbluebutton-html5/private/locales/ca.json
rename to bigbluebutton-html5/public/locales/ca.json
diff --git a/bigbluebutton-html5/private/locales/cs_CZ.json b/bigbluebutton-html5/public/locales/cs_CZ.json
similarity index 100%
rename from bigbluebutton-html5/private/locales/cs_CZ.json
rename to bigbluebutton-html5/public/locales/cs_CZ.json
diff --git a/bigbluebutton-html5/private/locales/da.json b/bigbluebutton-html5/public/locales/da.json
similarity index 100%
rename from bigbluebutton-html5/private/locales/da.json
rename to bigbluebutton-html5/public/locales/da.json
diff --git a/bigbluebutton-html5/private/locales/de.json b/bigbluebutton-html5/public/locales/de.json
similarity index 100%
rename from bigbluebutton-html5/private/locales/de.json
rename to bigbluebutton-html5/public/locales/de.json
diff --git a/bigbluebutton-html5/private/locales/el_GR.json b/bigbluebutton-html5/public/locales/el_GR.json
similarity index 100%
rename from bigbluebutton-html5/private/locales/el_GR.json
rename to bigbluebutton-html5/public/locales/el_GR.json
diff --git a/bigbluebutton-html5/private/locales/en.json b/bigbluebutton-html5/public/locales/en.json
similarity index 100%
rename from bigbluebutton-html5/private/locales/en.json
rename to bigbluebutton-html5/public/locales/en.json
diff --git a/bigbluebutton-html5/private/locales/eo.json b/bigbluebutton-html5/public/locales/eo.json
similarity index 100%
rename from bigbluebutton-html5/private/locales/eo.json
rename to bigbluebutton-html5/public/locales/eo.json
diff --git a/bigbluebutton-html5/private/locales/es.json b/bigbluebutton-html5/public/locales/es.json
similarity index 100%
rename from bigbluebutton-html5/private/locales/es.json
rename to bigbluebutton-html5/public/locales/es.json
diff --git a/bigbluebutton-html5/private/locales/es_ES.json b/bigbluebutton-html5/public/locales/es_ES.json
similarity index 100%
rename from bigbluebutton-html5/private/locales/es_ES.json
rename to bigbluebutton-html5/public/locales/es_ES.json
diff --git a/bigbluebutton-html5/private/locales/es_MX.json b/bigbluebutton-html5/public/locales/es_MX.json
similarity index 100%
rename from bigbluebutton-html5/private/locales/es_MX.json
rename to bigbluebutton-html5/public/locales/es_MX.json
diff --git a/bigbluebutton-html5/private/locales/et.json b/bigbluebutton-html5/public/locales/et.json
similarity index 100%
rename from bigbluebutton-html5/private/locales/et.json
rename to bigbluebutton-html5/public/locales/et.json
diff --git a/bigbluebutton-html5/private/locales/eu.json b/bigbluebutton-html5/public/locales/eu.json
similarity index 100%
rename from bigbluebutton-html5/private/locales/eu.json
rename to bigbluebutton-html5/public/locales/eu.json
diff --git a/bigbluebutton-html5/private/locales/fa_IR.json b/bigbluebutton-html5/public/locales/fa_IR.json
similarity index 100%
rename from bigbluebutton-html5/private/locales/fa_IR.json
rename to bigbluebutton-html5/public/locales/fa_IR.json
diff --git a/bigbluebutton-html5/private/locales/fi.json b/bigbluebutton-html5/public/locales/fi.json
similarity index 100%
rename from bigbluebutton-html5/private/locales/fi.json
rename to bigbluebutton-html5/public/locales/fi.json
diff --git a/bigbluebutton-html5/private/locales/fr.json b/bigbluebutton-html5/public/locales/fr.json
similarity index 100%
rename from bigbluebutton-html5/private/locales/fr.json
rename to bigbluebutton-html5/public/locales/fr.json
diff --git a/bigbluebutton-html5/private/locales/gl.json b/bigbluebutton-html5/public/locales/gl.json
similarity index 100%
rename from bigbluebutton-html5/private/locales/gl.json
rename to bigbluebutton-html5/public/locales/gl.json
diff --git a/bigbluebutton-html5/private/locales/he.json b/bigbluebutton-html5/public/locales/he.json
similarity index 100%
rename from bigbluebutton-html5/private/locales/he.json
rename to bigbluebutton-html5/public/locales/he.json
diff --git a/bigbluebutton-html5/private/locales/hi_IN.json b/bigbluebutton-html5/public/locales/hi_IN.json
similarity index 100%
rename from bigbluebutton-html5/private/locales/hi_IN.json
rename to bigbluebutton-html5/public/locales/hi_IN.json
diff --git a/bigbluebutton-html5/private/locales/hr.json b/bigbluebutton-html5/public/locales/hr.json
similarity index 100%
rename from bigbluebutton-html5/private/locales/hr.json
rename to bigbluebutton-html5/public/locales/hr.json
diff --git a/bigbluebutton-html5/private/locales/hu_HU.json b/bigbluebutton-html5/public/locales/hu_HU.json
similarity index 100%
rename from bigbluebutton-html5/private/locales/hu_HU.json
rename to bigbluebutton-html5/public/locales/hu_HU.json
diff --git a/bigbluebutton-html5/private/locales/hy.json b/bigbluebutton-html5/public/locales/hy.json
similarity index 100%
rename from bigbluebutton-html5/private/locales/hy.json
rename to bigbluebutton-html5/public/locales/hy.json
diff --git a/bigbluebutton-html5/private/locales/id.json b/bigbluebutton-html5/public/locales/id.json
similarity index 100%
rename from bigbluebutton-html5/private/locales/id.json
rename to bigbluebutton-html5/public/locales/id.json
diff --git a/bigbluebutton-html5/private/locales/it_IT.json b/bigbluebutton-html5/public/locales/it_IT.json
similarity index 100%
rename from bigbluebutton-html5/private/locales/it_IT.json
rename to bigbluebutton-html5/public/locales/it_IT.json
diff --git a/bigbluebutton-html5/private/locales/ja.json b/bigbluebutton-html5/public/locales/ja.json
similarity index 100%
rename from bigbluebutton-html5/private/locales/ja.json
rename to bigbluebutton-html5/public/locales/ja.json
diff --git a/bigbluebutton-html5/private/locales/ka.json b/bigbluebutton-html5/public/locales/ka.json
similarity index 100%
rename from bigbluebutton-html5/private/locales/ka.json
rename to bigbluebutton-html5/public/locales/ka.json
diff --git a/bigbluebutton-html5/private/locales/kk.json b/bigbluebutton-html5/public/locales/kk.json
similarity index 100%
rename from bigbluebutton-html5/private/locales/kk.json
rename to bigbluebutton-html5/public/locales/kk.json
diff --git a/bigbluebutton-html5/private/locales/km.json b/bigbluebutton-html5/public/locales/km.json
similarity index 100%
rename from bigbluebutton-html5/private/locales/km.json
rename to bigbluebutton-html5/public/locales/km.json
diff --git a/bigbluebutton-html5/private/locales/kn.json b/bigbluebutton-html5/public/locales/kn.json
similarity index 100%
rename from bigbluebutton-html5/private/locales/kn.json
rename to bigbluebutton-html5/public/locales/kn.json
diff --git a/bigbluebutton-html5/private/locales/ko_KR.json b/bigbluebutton-html5/public/locales/ko_KR.json
similarity index 100%
rename from bigbluebutton-html5/private/locales/ko_KR.json
rename to bigbluebutton-html5/public/locales/ko_KR.json
diff --git a/bigbluebutton-html5/private/locales/lo_LA.json b/bigbluebutton-html5/public/locales/lo_LA.json
similarity index 100%
rename from bigbluebutton-html5/private/locales/lo_LA.json
rename to bigbluebutton-html5/public/locales/lo_LA.json
diff --git a/bigbluebutton-html5/private/locales/lt_LT.json b/bigbluebutton-html5/public/locales/lt_LT.json
similarity index 100%
rename from bigbluebutton-html5/private/locales/lt_LT.json
rename to bigbluebutton-html5/public/locales/lt_LT.json
diff --git a/bigbluebutton-html5/private/locales/lv.json b/bigbluebutton-html5/public/locales/lv.json
similarity index 100%
rename from bigbluebutton-html5/private/locales/lv.json
rename to bigbluebutton-html5/public/locales/lv.json
diff --git a/bigbluebutton-html5/private/locales/mn_MN.json b/bigbluebutton-html5/public/locales/mn_MN.json
similarity index 100%
rename from bigbluebutton-html5/private/locales/mn_MN.json
rename to bigbluebutton-html5/public/locales/mn_MN.json
diff --git a/bigbluebutton-html5/private/locales/nb_NO.json b/bigbluebutton-html5/public/locales/nb_NO.json
similarity index 100%
rename from bigbluebutton-html5/private/locales/nb_NO.json
rename to bigbluebutton-html5/public/locales/nb_NO.json
diff --git a/bigbluebutton-html5/private/locales/nl.json b/bigbluebutton-html5/public/locales/nl.json
similarity index 100%
rename from bigbluebutton-html5/private/locales/nl.json
rename to bigbluebutton-html5/public/locales/nl.json
diff --git a/bigbluebutton-html5/private/locales/oc.json b/bigbluebutton-html5/public/locales/oc.json
similarity index 100%
rename from bigbluebutton-html5/private/locales/oc.json
rename to bigbluebutton-html5/public/locales/oc.json
diff --git a/bigbluebutton-html5/private/locales/pl_PL.json b/bigbluebutton-html5/public/locales/pl_PL.json
similarity index 100%
rename from bigbluebutton-html5/private/locales/pl_PL.json
rename to bigbluebutton-html5/public/locales/pl_PL.json
diff --git a/bigbluebutton-html5/private/locales/pt.json b/bigbluebutton-html5/public/locales/pt.json
similarity index 100%
rename from bigbluebutton-html5/private/locales/pt.json
rename to bigbluebutton-html5/public/locales/pt.json
diff --git a/bigbluebutton-html5/private/locales/pt_BR.json b/bigbluebutton-html5/public/locales/pt_BR.json
similarity index 100%
rename from bigbluebutton-html5/private/locales/pt_BR.json
rename to bigbluebutton-html5/public/locales/pt_BR.json
diff --git a/bigbluebutton-html5/private/locales/ro_RO.json b/bigbluebutton-html5/public/locales/ro_RO.json
similarity index 100%
rename from bigbluebutton-html5/private/locales/ro_RO.json
rename to bigbluebutton-html5/public/locales/ro_RO.json
diff --git a/bigbluebutton-html5/private/locales/ru.json b/bigbluebutton-html5/public/locales/ru.json
similarity index 100%
rename from bigbluebutton-html5/private/locales/ru.json
rename to bigbluebutton-html5/public/locales/ru.json
diff --git a/bigbluebutton-html5/private/locales/ru_RU.json b/bigbluebutton-html5/public/locales/ru_RU.json
similarity index 100%
rename from bigbluebutton-html5/private/locales/ru_RU.json
rename to bigbluebutton-html5/public/locales/ru_RU.json
diff --git a/bigbluebutton-html5/private/locales/sk_SK.json b/bigbluebutton-html5/public/locales/sk_SK.json
similarity index 100%
rename from bigbluebutton-html5/private/locales/sk_SK.json
rename to bigbluebutton-html5/public/locales/sk_SK.json
diff --git a/bigbluebutton-html5/private/locales/sl.json b/bigbluebutton-html5/public/locales/sl.json
similarity index 100%
rename from bigbluebutton-html5/private/locales/sl.json
rename to bigbluebutton-html5/public/locales/sl.json
diff --git a/bigbluebutton-html5/private/locales/sr.json b/bigbluebutton-html5/public/locales/sr.json
similarity index 100%
rename from bigbluebutton-html5/private/locales/sr.json
rename to bigbluebutton-html5/public/locales/sr.json
diff --git a/bigbluebutton-html5/private/locales/sv_SE.json b/bigbluebutton-html5/public/locales/sv_SE.json
similarity index 100%
rename from bigbluebutton-html5/private/locales/sv_SE.json
rename to bigbluebutton-html5/public/locales/sv_SE.json
diff --git a/bigbluebutton-html5/private/locales/te.json b/bigbluebutton-html5/public/locales/te.json
similarity index 100%
rename from bigbluebutton-html5/private/locales/te.json
rename to bigbluebutton-html5/public/locales/te.json
diff --git a/bigbluebutton-html5/private/locales/th.json b/bigbluebutton-html5/public/locales/th.json
similarity index 100%
rename from bigbluebutton-html5/private/locales/th.json
rename to bigbluebutton-html5/public/locales/th.json
diff --git a/bigbluebutton-html5/private/locales/th_TH.json b/bigbluebutton-html5/public/locales/th_TH.json
similarity index 100%
rename from bigbluebutton-html5/private/locales/th_TH.json
rename to bigbluebutton-html5/public/locales/th_TH.json
diff --git a/bigbluebutton-html5/private/locales/tr.json b/bigbluebutton-html5/public/locales/tr.json
similarity index 100%
rename from bigbluebutton-html5/private/locales/tr.json
rename to bigbluebutton-html5/public/locales/tr.json
diff --git a/bigbluebutton-html5/private/locales/tr_TR.json b/bigbluebutton-html5/public/locales/tr_TR.json
similarity index 100%
rename from bigbluebutton-html5/private/locales/tr_TR.json
rename to bigbluebutton-html5/public/locales/tr_TR.json
diff --git a/bigbluebutton-html5/private/locales/uk_UA.json b/bigbluebutton-html5/public/locales/uk_UA.json
similarity index 100%
rename from bigbluebutton-html5/private/locales/uk_UA.json
rename to bigbluebutton-html5/public/locales/uk_UA.json
diff --git a/bigbluebutton-html5/private/locales/vi.json b/bigbluebutton-html5/public/locales/vi.json
similarity index 100%
rename from bigbluebutton-html5/private/locales/vi.json
rename to bigbluebutton-html5/public/locales/vi.json
diff --git a/bigbluebutton-html5/private/locales/vi_VN.json b/bigbluebutton-html5/public/locales/vi_VN.json
similarity index 100%
rename from bigbluebutton-html5/private/locales/vi_VN.json
rename to bigbluebutton-html5/public/locales/vi_VN.json
diff --git a/bigbluebutton-html5/private/locales/zh_CN.json b/bigbluebutton-html5/public/locales/zh_CN.json
similarity index 100%
rename from bigbluebutton-html5/private/locales/zh_CN.json
rename to bigbluebutton-html5/public/locales/zh_CN.json
diff --git a/bigbluebutton-html5/private/locales/zh_TW.json b/bigbluebutton-html5/public/locales/zh_TW.json
similarity index 100%
rename from bigbluebutton-html5/private/locales/zh_TW.json
rename to bigbluebutton-html5/public/locales/zh_TW.json
diff --git a/bigbluebutton-html5/transifex.sh b/bigbluebutton-html5/transifex.sh
index de1efe3eaa73f91ca62b80f75b450bf59da70587..b11dc50f7ac3f69058c0106abd1dfa425230b819 100755
--- a/bigbluebutton-html5/transifex.sh
+++ b/bigbluebutton-html5/transifex.sh
@@ -5,6 +5,14 @@ RED='\033[0;31m'
 GREEN='\033[1;32m'
 NC='\033[0m'
 SOURCE_LANGUAGE="en"
+LOCALES_DIRECTORY="./public/locales"
+PULL_SOURCE=false
+
+if [[ ! -e $LOCALES_DIRECTORY ]]; then
+    echo -e "Directory ${RED}$LOCALES_DIRECTORY${NC} does not exist, creating"
+    mkdir $LOCALES_DIRECTORY
+    PULL_SOURCE=true
+fi
 
 if [ "$#" = 0 ]
 then
@@ -33,19 +41,19 @@ else
           echo "$AVAILABLE_TRANSLATIONS" | while read l
             do
               LOCALE=$( echo "$l" | tr -d '[:space:]' )
-              if [ "$LOCALE" == "$SOURCE_LANGUAGE" ]; then
-                continue # do not pull the source file
+              if [ "$LOCALE" == "$SOURCE_LANGUAGE" ] && [ "$PULL_SOURCE" == false ]; then
+                continue # only pull source file if locales folder did not exist
               fi
               TRANSLATION=$(curl -L --user "$USER":"$PW" -X GET "https://www.transifex.com/api/2/project/bigbluebutton-v23-html5-client/resource/enjson/translation/$LOCALE/?mode=onlytranslated&file")
               NO_EMPTY_STRINGS=$(echo "$TRANSLATION" | sed '/: *\"\"/D' | sed '/}$/D')
-              if [ $(echo "$NO_EMPTY_STRINGS" | wc -l) == 1 ]
+              if [ $(echo "$NO_EMPTY_STRINGS" | wc -l) -lt 100 ]
               then
-                echo -e "${RED}WARN:${NC} translation file $LOCALE.json is empty\n${RED}WARN:${NC} $LOCALE.json not created"
+                echo -e "${RED}WARN:${NC} translation file $LOCALE.json contains less than 100 lines\n${RED}WARN:${NC} $LOCALE.json not created"
                 continue
               else
                 NO_TRAILING_COMMA=$(echo "$NO_EMPTY_STRINGS" | sed  '$ s/,$//')
-                echo "$NO_TRAILING_COMMA" > ./private/locales/"$LOCALE".json
-                echo -e "\n}\n" >> ./private/locales/"$LOCALE".json
+                echo "$NO_TRAILING_COMMA" > "$LOCALES_DIRECTORY/$LOCALE".json
+                echo -e "\n}\n" >> "$LOCALES_DIRECTORY/$LOCALE".json
                 echo -e "Added translation file $LOCALE.json : ${GREEN}✓${NC}"
               fi
             done
@@ -56,13 +64,13 @@ else
             echo -e "${RED}Err${NC}: Translations not found for locale ->${RED}$ARG${NC}<-"
           else
             NO_EMPTY_STRINGS=$(echo "$TRANSLATION" | sed '/: *\"\"/D' | sed '/}$/D')
-            if [ $(echo "$NO_EMPTY_STRINGS" | wc -l) == 1 ]
+            if [ $(echo "$NO_EMPTY_STRINGS" | wc -l) -lt 100 ]
             then
-              echo -e "${RED}WARN:${NC} translation file $ARG.json is empty\n${RED}WARN:${NC} $ARG.json not created"
+              echo -e "${RED}WARN:${NC} translation file $ARG.json contains less than 100 lines\n${RED}WARN:${NC} $ARG.json not created"
             else
               NO_TRAILING_COMMA=$(echo "$NO_EMPTY_STRINGS" | sed  '$ s/,//')
-              echo "$NO_TRAILING_COMMA" > ./private/locales/"$ARG".json
-              echo -e "\n}\n" >> ./private/locales/"$ARG".json
+              echo "$NO_TRAILING_COMMA" > "$LOCALES_DIRECTORY/$ARG".json
+              echo -e "\n}\n" >> "$LOCALES_DIRECTORY/$ARG".json
               echo -e "Added translation file $ARG.json :${GREEN} ✓${NC}"
             fi
           fi