anchor.diff:          '';
         };
   
  +      enableNmea = mkOption {
  +        type = types.bool;
  +        default = true;
  +        description = ''
  +          Whether to fetch location from NMEA sources on local network.
  +        '';
  +      };
  +
  +      enable3G = mkOption {
  +        type = types.bool;
  +        default = true;
  +        description = ''
  +          Whether to enable 3G source.
  +        '';
  +      };
  +
  +      enableCDMA = mkOption {
  +        type = types.bool;
  +        default = true;
  +        description = ''
  +          Whether to enable CDMA source.
  +        '';
  +      };
  +
  +      enableModemGPS = mkOption {
  +        type = types.bool;
  +        default = true;
  +        description = ''
  +          Whether to enable Modem-GPS source.
  +        '';
  +      };
  +
  +      enableWifi = mkOption {
  +        type = types.bool;
  +        default = true;
  +        description = ''
  +          Whether to enable WiFi source.
  +        '';
  +      };
  +
  +      geoProviderUrl = mkOption {
  +        type = types.str;
  +        default = "https://location.services.mozilla.com/v1/geolocate?key=geoclue";
  +        example = "https://www.googleapis.com/geolocation/v1/geolocate?key=YOUR_KEY";
  +        description = ''
  +          The url to the wifi GeoLocation Service.
  +        '';
  +      };
  +
  +      submitData = mkOption {
  +        type = types.bool;
  +        default = false;
  +        description = ''
  +          Whether to submit data to a GeoLocation Service.
  +        '';
  +      };
  +
  +      submissionUrl = mkOption {
  +        type = types.str;
  +        default = "https://location.services.mozilla.com/v1/submit?key=geoclue";
  +        description = ''
  +          The url to submit data to a GeoLocation Service.
  +        '';
  +      };
  +
  +      submissionNick = mkOption {
  +        type = types.str;
  +        default = "geoclue";
  +        description = ''
  +          A nickname to submit network data with.
  +          Must be 2-32 characters long.
  +        '';
  +      };
  +
  +      appConfig = mkOption {
  +        type = types.loaOf appConfigModule;
  +        default = {};
  +        example = literalExample ''
  +          "com.github.app" = {
  +            isAllowed = true;
  +            isSystem = true;
  +            users = [ "300" ];
  +          };
  +        '';
  +        description = ''
  +          Specify extra settings per application.
  +        '';
  +      };
  +
       };
   
     };
   
   
     ###### implementation
  -  config = mkIf config.services.geoclue2.enable {
  +  config = mkIf cfg.enable {
   
       environment.systemPackages = [ package ];
   
       services.dbus.packages = [ package ];
   
       systemd.packages = [ package ];
  -  
  +
  +    # restart geoclue service when the configuration changes
  +    systemd.services."geoclue".restartTriggers = [
  +      config.environment.etc."geoclue/geoclue.conf".source
  +    ];
  +
       # this needs to run as a user service, since it's associated with the
       # user who is making the requests
  -    systemd.user.services = mkIf config.services.geoclue2.enableDemoAgent { 
  +    systemd.user.services = mkIf cfg.enableDemoAgent {
         "geoclue-agent" = {
           description = "Geoclue agent";
           script = "${package}/libexec/geoclue-2.0/demos/agent";
  
positive.code:       };
      };
  
      environment.etc."geoclue/geoclue.conf".source = "${package}/etc/geoclue/geoclue.conf";
    };
  
  }
  
negative.code: let
    # the demo agent isn't built by default, but we need it here
    package = pkgs.geoclue2.override { withDemoAgent = config.services.geoclue2.enableDemoAgent; };
  
    cfg = config.services.geoclue2;
  
    defaultWhitelist = [ "gnome-shell" "io.elementary.desktop.agent-geoclue2" ];
  
    appConfigModule = types.submodule ({ name, ... }: {
      options = {
        desktopID = mkOption {
          type = types.str;
          description = "Desktop ID of the application.";
        };
  
        isAllowed = mkOption {
          type = types.bool;
          default = null;
          description = ''
            Whether the application will be allowed access to location information.
          '';
        };
  
        isSystem = mkOption {
          type = types.bool;
          default = null;
          description = ''
            Whether the application is a system component or not.
          '';
        };
  
        users = mkOption {
          type = types.listOf types.str;
          default = [];
          description = ''
            List of UIDs of all users for which this application is allowed location
            info access, Defaults to an empty string to allow it for all users.
          '';
        };
      };
  
      config.desktopID = mkDefault name;
    });
  
    appConfigToINICompatible = _: { desktopID, isAllowed, isSystem, users, ... }: {
      name = desktopID;
      value = {
        allowed = isAllowed;
        system = isSystem;
        users = concatStringsSep ";" users;
      };
    };
  
  in
  {
  
  