Default Profile Directory Doesn’t Work in Firefox 46

NOTE: I updated this code on April 18, 2017 in an attempt to be more robust and not depend on Firefox preference. If you are using remote autoconfig, make sure this code is in your local autoconfig, not in the remote version. And the correct directory for the default profile is defaults/profile, not defaults/browser/profile.

It was recently discovered that support for using the defaults/profile directory to prepopulate a Firefox profile was removed in Firefox 46.

Here’s an AutoConfig file that adds back the functionality:

//
const {classes: Cc, interfaces: Ci, utils: Cu} = Components;
Cu.import("resource://gre/modules/Services.jsm");
Cu.import("resource://gre/modules/FileUtils.jsm");

var profileDir = Services.dirsvc.get("ProfD", Ci.nsIFile);
var certDBFile = profileDir.clone();
certDBFile.append("cert8.db")
// If cert8.db isn't there, it's a new profile
if (!certDBFile.exists()) {
  var defaultProfileDir = Services.dirsvc.get("GreD", Ci.nsIFile);
  defaultProfileDir.append("defaults");
  defaultProfileDir.append("profile");
  try {
    copyDir(defaultProfileDir, profileDir);
  } catch (e) {
    Components.utils.reportError(e);
  }
}
 
function copyDir(aOriginal, aDestination) {
  var enumerator = aOriginal.directoryEntries;
  while (enumerator.hasMoreElements()) {
    var file = enumerator.getNext().QueryInterface(Components.interfaces.nsIFile);
    if (file.isDirectory()) {
      var subdir = aDestination.clone();
      subdir.append(file.leafName);
      try {
        subdir.create(Ci.nsIFile.DIRECTORY_TYPE, FileUtils.PERMS_DIRECTORY);
        copyDir(file, subdir);
      } catch (e) {
        Components.utils.reportError(e);
      }
    } else {
      try {
        file.copyTo(aDestination, null);
      } catch (e) {
        Components.utils.reportError(e);
      }
    }
  }
}

This should work for most file types, although it probably won’t work for bookmarks.html

I’ll also be adding this functionality to the next version of the CCK2 which will be released later today.

Please note: I reserve the right to delete comments that are offensive or off-topic.

Leave a Reply

Your email address will not be published. Required fields are marked *

81 thoughts on “Default Profile Directory Doesn’t Work in Firefox 46

  1. Mike, what’s your recommended way to cope with bootstrapped extensions?

    I looked into extensions.bootstrappedAddons, there are extensions that require their stuff to be written there in order to show up immediately (e.g. uBlock Origin). According to my knowledge I have to generate a json object containing the extension’s id, type, version and multiprocessCompatible variable. I already managed to get the relevant data out of a xpi, but I’m unsure how to achieve

    {“uBlock0@raymondhill.net”:{“version”:”1.7.4″,”type”:”extension”,”descriptor”:”C:\\Program Files (x86)\\Mozilla Firefox\\profile\\extensions\\uBlock0@raymondhill.net.xpi”,”multiprocessCompatible”:true,”runInSafeMode”:false}}

    for the prefs.js setting.
    How would you do it?

    • How does this part of your code look?

      if (!certDBFile.exists()) {
      var defaultProfileDir = Services.dirsvc.get(“GreD”, Ci.nsIFile);
      defaultProfileDir.append(“defaults”);
      defaultProfileDir.append(“profile”);
      try {
      copyDir(defaultProfileDir, profileDir);
      } catch (e) {
      Components.utils.reportError(e);
      }
      }

      Don’t forget you would have to add defaultProfileDir.append(“browser”); if you want to use the directory you mention.

  2. This sucks, I just have a simple batch file that would install and copy the file to Firefox directory and when the user launches Firefox for the first time the file in the browser folder would just copy to the profile. Is there a easier way doing this without modifying all this stuff? It’s very confusing.

  3. Hello,

    I’m trying to implement the autoconfig functionality with the config file you have provided, but I seem to be missing something.

    I’ve created an autoconfig.js file inside of C:\Program Files (x86)\Mozilla Firefox\defaults\pref with the following content:
    pref(“general.config.filename”, “firefox.cfg”);
    pref(“general.config.obscure_value”, 0);

    I’ve created firefox.cfg at the root of C:\Program Files (x86)\Mozilla Firefox with the content directly from your post.

    My profile is stored at C:\Program Files (x86)\Mozilla Firefox\browser\defaults\profile, per the standard that functioned up until Firefox 46, which is the release that they removed the default profile functionality in.

    Thoughts on what I’m missing here?

    Thanks!

    • My code uses defaults/profile not browser/defaults/profile.

      You can add defaultProfileDir.append(“browser”); right after querying the directory for that to work.

  4. Hi Mike, I was wondering if you knew how to add a default mailto: handler. I’d like to configure the organization’s webmail as default handler for mailto: links, so I’ve tried searching for options on about:config but I only stumbled upon the ones shipped with Firefox and not mine. Thanks for the awesome CCK2, it’s really useful!

  5. Some of files was copied with this script, but mimetypes.rdf – not copied or was replaced.
    How to add to default mimetypes.rdf file records like this:

    ………

    ………………..
    In existing profile I can edit mimetype.rdf, but I want to make modifications in default file for new profiles.
    Before version 46.0 profile was created from “defaults” folder but now this didn`t work

  6. I stuck an autoconfig.js file with the content from your post above with the copyDir function and nothing seems to happen. I tried multiple locations for the profile files, including:
    c:\Program Files\Mozilla Firefox\defaults\profile

    Are there any other changes needed to get the autoconfig to work?

    The only reason I need the above is that I am having one issue with CCK2 (which worked great otherwise). We use self-signed certificates, so was using Cert Overrides tab to add them. The problem is that if the certificate server is down when the browser is initially launched, the certificates are never imported for that user until the user’s Mozilla profile is cleaned up and Firefox is re-launched when the server is up. The only thing I can think of to get around this is to get the copy profile working again which we used prior to Firefox 46.

    Any ideas?
    Thank You.

    • Did you make the changes to defaults/pref to enable the autoconfig? Can you add some prefs to autoconfig?

      As far as the self signed certs go, the way it works is that it does a preconnect to the server in question and marks them as valid.

      It should be a one time thing though…

      I think what I’ll look into is allowing the CCK2 to create cert override.txt

      • I don’t have any experience customizing Firefox, but all I did was create an autoconfig.js file with the exact contents from the code above (the copyDir function) and stuck it in defaults/pref. There is nothing else in that file. What else do I need to do to enable autoconfig because nothing seems to be happening. Every time I read about autoconfig, they always mention creating and referencing mozilla.cfg in the autoconfig, but all I want to do is copy the default profile. Do I still need a mozilla.cfg in this case?

        For the certificate issue, the preconnect takes place when the user launches the browser. In our disconnected system, there is a decent chance that the server may not be available when they launch the browser. Because it is a one-time thing, the preconnect fails and the overrides never get added. If the cert_override.txt is a way around this, that would definitely work.

        • Just tested, the autoconfig.js is working because it does find the mozilla.cfg and I can set preferences.

          The above code still doesn’t copy my profile for new users though. Is there a way to debug the autoconfig script? Alerts don’t work, is there a way to output text to a log file?

            • It is copying the files from the default profile fine, but…

              Once the browser is initially started, it overwrites the preferences that were copied in. The only thing that is working for me are the certificates and bookmarks. All about:config preferences are overwritten and the initial display of the menu/toolbar does not work.

              I guess I’ll have to use a combination of CCK2 and the profile copy of the certificates (cert_override.txt and cert8.db) in order to get everything I need. This is getting messy.

              • You can use the CCK2 to do the same thing as cert overrides and cert8.db.

                Is there something specific that’s not working?

                • Like I mentioned in my original post, using the overrides requires the certificate server to be available when the user first launches Firefox. In our system this is very common. Since this is a one-time thing, the overrides never get added.

  7. It work for me. Thank you.

    By the way I use >>>lockPref(“browser.startup.homepage_override.mstone”,”ignore”);<<>>if (!Services.prefs.prefHasUserValue(“extensions.lastPlatformVersion”)) {<<<

  8. Hi Mike,
    I am trying to distribute Firefox 50 with a default profile by adding an edited localstore.rdf.
    The file is getting copied over within the new profile thanks to your above script, but with the new profile it doesn’t seem to have any effect. Also, in other new profiles without configuration, localstore.rdf doesn’t appear anymore.
    Do you know if this has changed recently?

    • I think with Firefox 50 localstore.rdf was replaced with another file.

      My suggestion would be that you check a new profile and look for a different file. I’ll check as well.

      • Diving into this subject again. Found out that there are at least 2 files which refer to the UI.
        First there is prefs.js, in which there is the pref: browser.uiCustomization.state
        Secondly there is xulstore.json.
        I have tried to set the pref with CCK and putting xulstore.json in %INSTALLDIR%\defaults\profile. Without the above script the file gets copied over to the new profile (not needed anymore?), but somehow this doesn’t have any effect. I don’t know what CCK exactly is doing at first profilecreation, at least it makes Firefox restart once.
        Any insight Mike?

  9. Hi Mike,

    I used the below userChrome.css code for FF 45 to hide the ‘Help, About, Check for updates’ button. This code does not work for version 50, nor can I get anything to work in a userChrome.css file now.

    #updateSeparator, #checkForUpdates { display: none !important; }
    #enableAppUpdate { display: none !important; }

    Any ideas on what broke and how to hide the button in version 50?

    Thanks.

  10. When I try to download CCK2 I get “Firefox prevented this site from asking you to install software on you computer.” I click on Allow and I get this message ” github.com The Add-on could not be downloaded because of a connection failure” Any idea how I can get around this error.
    sarah

  11. The script code above works great, but is there another way to determine if this is the first time the user launched Firefox instead of:
    Services.prefs.prefHasUserValue(“browser.startup.homepage_override.mstone”)

    The problem is that I disable startup tabs using the cck2 wizard:
    “noWelcomePage”: true
    “noUpgradePage”: true

    This causes that copy profile block of code to run every time, including users with existing profiles (which get overwritten).

    Thank You.

    • Good point. I’ll see if I can come up with a better solution. Note that this functionality is built into the CCK2, you don’t need the script. But the CCK2 uses mstone as well.

  12. Hi,
    Thanks for this post, I have been looking everywhere for a solution to this problem. Forgive me, but I am an infrastructure specialist, not a script specialist, however I have worked out how to use other’s scripts regularly in my job.
    Would you mind just clarifying for me how I would use the above code please. I am assuming I would save it as somefilename.js, but could you please advise where I would save it and how I would call it (e.g. would it be a line in the local-settings.js?)
    Many thanks for your help

  13. Ok I figured it out, but it’s not working for what I need to achieve. I have copied your code to “C:\Program Files\Mozilla Firefox\firefox.cfg and created an autoconfig.js file saved to \defaults\pref which calls the firefox.cfg file as described above.
    Can you tell me if it is possible to copy a pre-configured cert8.db file to the defaults\profile folder and for it to copy itself to all new user profiles and register the certificates please?
    I am trying to prevent the “your connection is not secure” message our Firefox users receive and we are going through a Websense proxy. When I manually add the required certificates to Firefox it works, but I need to automate this as part of our build.
    Many thanks

      • It’s hard to say Mike. The only file in there is my cert8.db file and when I login as a new user and navigate to their ..\Firefox\Profiles\xxxx.default folder I can see the cert8.db file in there with today’s timestamp, but I’m unsure if this is the default one or the one copied over. When I open Firefox as that user and go to Google I get the “your connection is not secure” message

        • Try creating a file with a unique name “foo.txt” and put that in defaults/profile.

          Then we can at least verify that the copy is working.

          then we can figure out what to debug.

          • Hi Mike,
            I tried that and the file didn’t copy across to the new user’s profile. Btw I don’t know if it makes a difference, but I am using Firefox 51.0 64-bit with Windows 10 Pro

            • OK, so it looks like the default profile code isn’t running.

              I’ll do some testing to make sure we’re still good on 51 and send you files.

              • Thanks. I’ve just noticed something – the AppData\Roaming\Mozilla\… folders don’t get created until the new user has opened Firefox. Is this expected behaviour?

              • Mike,

                I’m experiencing the same problem. I have placed the code at the end of our existing autoconfig file and tried creating a new profile. The new profile does not pick up any of the files located in the browser\defaults\profile directory, including cert8.db, secmod.db, a test.txt, as well as a few others.

                I tried placing the code in a try/catch block, but nothing is being logged. The other autoconfig values apply normally.

                We’re on Firefox ESR 52.0.2 32-bit.

                Any ideas?

                  • Thanks – please let us know what you come up with. This is kind of biting us in the butt right now. Do you happen to know if CCK2 is impacted by the problem as well?

                    • If the problem is the preference code, then yes. I’ll be intergrating the new code I just wrote into the CCK2.

                    • I’ve updated this post with new code. Have you tried it?

                      Are you using a remote autoconfig or local autoconfig?

                  • I just did a test with a clean profile (52.0.2) and the defaults/profile code is working for me.

                    Are you by chance using the CCK2 to turn off the override page?

                    • I’ve just tried the updated code, but still having no luck.

                      The files I’m trying to have copied at new profile creation are located in C:\Program Files (x86)\Mozilla Firefox\browser\defaults\profile. Specifically, I have a cert8.db and secmod.db in there.

                      I’m creating a brand new profile when testing.

                      For what it’s worth, I’d previously identified that the old code relied on the browser.startup.homepage_override.mstone preference (which I set to ignore in my autoconfig) and had already tried changing it to something else.

                      Not sure if I’m missing anything obvious, or something about the code isn’t working on certain systems. Is there anything else I can check?

                    • Can you add some printfs in the code and make sure things are being hit?

                      You can use Components.utils.reportError(“HERE”) and then you should be able to see the results on the Browser Console (Ctrl+Shift+J) after startup.

                      In particular, verify that we are going down the path to copy the files, so put a Components.utils.reportError(“Copying Files”) before the copyDir statement

                      Also you might check to see if there are any other errors on the console.

                    • Okay… two problems I identified.

                      1. The certDBFile.exists() check seems to be returning true. The code that follows it isn’t firing.

                      2. When I commented out the check to force the code to run, I’m getting the following immediately prior to copyDir:

                      [Exception… “Component returned failure code: 0x80520012 (NS_ERROR_FILE_NOT_FOUND) [nsIFile.directoryEntries]” nsresult: “0x80520012 (NS_ERROR_FILE_NOT_FOUND)” location: “JS frame :: x-bogus://XPConnect/Sandbox :: copyDir :: line 177” data: no] (unknown)
                      copyDir x-bogus://XPConnect/Sandbox:177:7
                      x-bogus://XPConnect/Sandbox:167:3

                    • So it looks like you have the file location wrong.

                      It should be defaults/profile, not browser/defaults/profile.

                      As far as certdb existing, that’s weird. It shouldn’t if this is a brand new profile (is it)?

                    • Okay… I added an append for ‘browser’ and it’s successfully copying now (with the certDBFile.exists() check still commented out).

                      Yes, I’m using a brand new profile for each test.

                      One thing I noted during the test with the successful copy, is that although the secmod.db file correctly copied, the extra security module it contains was not loaded into Firefox. Closing Firefox and restarting it with the same profile (second run of that profile) worked as expected, and the module was loaded. It almost seems like a default secmod.db was created, Firefox loaded using the default, and then the autoconfig code copied over the ‘custom’ default file. This would also explain the cert8.db check showing that the file already exists…

                    • Interesting. So if you don’t mind, I’d like to give you some more debug code to try to figure this out.

                      I’ll email it separately.

                    • Actually, here is the code. If you could put this after the
                      var profileDir = Services.dirsvc.get(“ProfD”, Ci.nsIFile);
                      line
                      var enumerator = profileDir.directoryEntries;
                      while (enumerator.hasMoreElements()) {
                      var file = enumerator.getNext().QueryInterface(Components.interfaces.nsIFile);
                      Components.utils.reportError(file.path);
                      }

                      This will report on the console all the files that are in your new profile directory.

                      I want to compare the files in your new profile directory with mine.

  14. Thanks for this! Again you are a life-saver for keeping FF deployable.
    Added this to my autoconfig files, and it works great. With a few additions you can make a separate directory for files to copy every time, I think 🙂

  15. Hi,

    First thanks for this workaround that works like a charm !

    I currently preparing deployment of Thunderbird 52, but it seems that the defaults/profile folder does not prepopulate new profiles anymore, like in Firefox.

    I tried to add your workaround but it seems not working.

    Do you know if there is another solution for restoring this functionnality in Thunderbird ?

    Thanks in advance.

  16. C:\Users\username\AppData\Roaming\Mozilla\Firefox\Profiles\8639bogo.test12\blocklist.xml Sandbox:159
    C:\Users\username\AppData\Roaming\Mozilla\Firefox\Profiles\8639bogo.test12\cert8.db Sandbox:159
    C:\Users\username\AppData\Roaming\Mozilla\Firefox\Profiles\8639bogo.test12\compatibility.ini Sandbox:159
    C:\Users\username\AppData\Roaming\Mozilla\Firefox\Profiles\8639bogo.test12\crashes Sandbox:159
    C:\Users\username\AppData\Roaming\Mozilla\Firefox\Profiles\8639bogo.test12\extensions.ini Sandbox:159
    C:\Users\username\AppData\Roaming\Mozilla\Firefox\Profiles\8639bogo.test12\gmp Sandbox:159
    C:\Users\username\AppData\Roaming\Mozilla\Firefox\Profiles\8639bogo.test12\key3.db Sandbox:159
    C:\Users\username\AppData\Roaming\Mozilla\Firefox\Profiles\8639bogo.test12\minidumps Sandbox:159
    C:\Users\username\AppData\Roaming\Mozilla\Firefox\Profiles\8639bogo.test12\parent.lock Sandbox:159
    C:\Users\username\AppData\Roaming\Mozilla\Firefox\Profiles\8639bogo.test12\pluginreg.dat Sandbox:159
    C:\Users\username\AppData\Roaming\Mozilla\Firefox\Profiles\8639bogo.test12\prefs.js Sandbox:159
    C:\Users\username\AppData\Roaming\Mozilla\Firefox\Profiles\8639bogo.test12\secmod.db Sandbox:159
    C:\Users\username\AppData\Roaming\Mozilla\Firefox\Profiles\8639bogo.test12\times.json Sandbox:159
    Checking if new profile Sandbox:164
    Not a new profile Sandbox:179

    • Interesting. Is this Firefox 52? Here’s what I see on Firefox 52.

      I guess I’ll have to pick a different file to test.

      C:\Users\mkaply\AppData\Roaming\Mozilla\Firefox\Profiles\naalzin8.fsdafsdfsdafsda\compatibility.ini
      C:\Users\mkaply\AppData\Roaming\Mozilla\Firefox\Profiles\naalzin8.fsdafsdfsdafsda\crashes
      C:\Users\mkaply\AppData\Roaming\Mozilla\Firefox\Profiles\naalzin8.fsdafsdfsdafsda\minidumps
      C:\Users\mkaply\AppData\Roaming\Mozilla\Firefox\Profiles\naalzin8.fsdafsdfsdafsda\parent.lock
      C:\Users\mkaply\AppData\Roaming\Mozilla\Firefox\Profiles\naalzin8.fsdafsdfsdafsda\prefs.js
      C:\Users\mkaply\AppData\Roaming\Mozilla\Firefox\Profiles\naalzin8.fsdafsdfsdafsda\times.json

      • Yep… ESR 52.0.2, 32-bit.

        Weird problem. So it does seem that FF is loading with some defaults in place before the autoconfig code ever copies anything. I just wonder where they’re coming from.

      • Okay, I think I’ve got it figured out.

        My configuration loads a general.config.filename on the local drive (mozilla.cfg). mozilla.cfg then uses autoadmin.global_config_url to pull a centrally managed autoconfig from a network file:// path.

        I’d been placing the profile copy code into that network autoconfig. By moving the code into the mozilla.cfg, things are working as expected. I’m seeing the same default files as you, the cert8.db test works, and my default files are copied over. Mostly importantly, they are going into effect at Firefox startup – the security module I’ve got in secmod.db is correctly loaded.

        Bottom line is that something with the network autoconfig changes the startup and file creation/copy order.

        • That does make sense. The network request takes some time, so more startup is happening. I’ll update the post to make sure it’s clear this needs to go in the main mozilla config. And I’ll be more clear about the directory names.

          Thanks for your help debugging!

  17. Hello Mike,

    I need to deploy Front Motion Firefox 52.1 on multiple computer and i need to copy the cert8.db file to all user profiles.

    Can you please tell me exact steps i need to follow so that i can copy the cert8.db file.

    Thanks
    Evinrude

  18. Hi,

    I tried your workaround with Firefox ESR 45.8 : the files are not copied from C:\Program Files (x86)\Mozilla Firefox\defaults\Profile to new profiles… In this directory, i have a extensions.ini, a mimeTypes.rdf and a prefs.js : no one is copied…
    I have your autoconfig.js in C:\Program Files (x86)\Mozilla Firefox\defaults\pref.
    Any ideas ?
    Do you now how install an extension for all new profile ? Before, with XPI file or directory of unziping of this xpi, copied in the C:\Program Files (x86)\Mozilla Firefox\distribution\bundles\, that was working, but now…

    Best regards

    JY