the Chromium logo

The Chromium Projects

Enterprise policy

Here, we extract a few key points from the more general


Features can optionally be controlled by enterprise administrators. This requires a few additions to the code base. For example, consider Nearby Share:

  1. Add an entry to policy_template.json, for example, NearbyShareAllowed. Of note, dynamic_refresh means policy changes can take effect even while the user is logged in.

  2. Add a handler to, configuring the policy to affect a specific pref. For example, see NearbyShareAllowed (but beware its unorthodox handler).

  3. Use PrefService::IsManagedPreference() to determine if a feature is being controlled by enterprise policy. For example, we adjust the UI if Nearby Share is disallowed by policy.

Testing enterprise policy

To test an enterprise policy on ChromeOS quickly--without needing to set up a policy test server (see we can simply add a file to the DUT (see also linux-quick-start). For example, to set the NearbyShareAllowed policy value,

  1. ssh into your DUT,
  2. create the file /etc/opt/chrome/policies/managed/test_policy.json[^1],
  3. add {"NearbyShareAllowed": true},
  4. wait for the policy to refresh or click "Reload policies" at chrome://policy,
  5. confirm the correct policy value at chrome://policy on the DUT.

No special account is required on the DUT to perform this testing.

[^1]: For unofficial Chromium builds, this might need to be /etc/chromium/policies/managed/test_policy.json. See linux-quick-start.

Using the Enterprise Policies Admin Panel

This section describes the steps for setting a policy rule from the Admin panel, and seeing it applied on your managed device/account. Note that you can only login to the Admin panel with a user account, otherwise you will be stuck in the select accounts page.

Obtain a @managedchrome account

If you haven't already, obtain a @managedchrome account with "Super Admin" privileges by filling out the form at go/managed-chrome-account.

Alternatively, you can do this by asking someone on the team who does have a @managedchrome account with "Super Admin" privileges to:

  1. Login to the Admin panel with their @managedchrome account.
  2. Add a new user (this can be done in the Home page and expanding the "Users" card > "Add a user").
  3. Updating the newly created account with "Super Admin" privileges by searching for the username in the search box and clicking into the subpage, and then going to the "Admin roles and privileges" section.

Create an Organizational unit

An organizational unit should be created that your @managedchrome account will be within. Any policy updates you make to the organizational unit in the admin panel will be applied to accounts/devices within that unit.

Prior to creating a new unit, the account will default to the root parent unit. Your new organizational unit will be a descendent of the unit.

To create an organizational unit:

  1. Log into to the Admin panel with your @managedchrome account.
  2. Go to Directory > Organization units and add new organizational unit.
  3. Go to Directory > Users and navigate to your account.
  4. Click "Change Organizational Unit" and select the new unit that was created.

Setting an enterprise policy rule

If you want to make device policy changes, you need to go through OOBE on your test device and enterprise enroll your test device with the @managedchrome account. Then, ensure that you are logged in with your @managedchrome account and not guest.

After you have completed the previous steps, you are now ready to set policies via the admin panel and see the policies applied to your device/account. Ensure that whenever you apply a policy in the admin panel, you do so to the organizational unit your @managedchrome account is associated with, otherwise your device will see no change.


The following example runs through how to add a new policied Wi-Fi network that your managed chromebook can connect to without entering a passphrase on your chromebook. Policied Wi-Fi networks will display a building icon in its row in the list of available WiFi networks shown at the WiFi subpage of OS Settings on your managed on your device.

  1. Disconnect from the Wi-Fi network your test device is currently connected to, and forget it so that if the next time you try to connect to the Wi-Fi, you would have to re-enter the passphrase.
  2. Login to the Admin panel with your @managedchrome account on a device other than your test device.
  3. Go to Devices > Networks > Wi-Fi
  4. Ensure that the "Organizational unit" is the organizational unit you created.
  5. Click "Add WiFi", at which point you'll be taken to a form to add a Wifi.
  6. In the "Platform access" section, make the selections that fit your use case (likely "Chromebooks (by user)" and "Chromebooks (by device)".
  7. Enter a Wi-Fi Name and SSID. Note that the "SSID" is likely the name of the Wi-Fi that is shown to your test device.
  8. If your Wi-Fi requires a passphrase, you will likely have to change the "Security settings" in the "Details" section of the form. For WiFi at your home, for example, you may likely select a "Security Type" of "WPA/WPA2". Ensure you add the passphrase to the Wi-Fi in the form.
  9. Make any other desired changes.
  10. Click save.
  11. Log out of your chromebook and log back in.
  12. Go to OS Settings and the Wi-Fi network subpage, and you should be able to see the policied Wi-Fi network (if it is in range) with a building icon in the row.
  13. Try connecting, and you'll notice that you will be able to connect without having to enter a passphrase.

Building a local instance of the Network Admin Dpanel for development

This section describes how you can spin up a local instance of the Admin DPanel for Network related policy development. More details of this process can be found here.

  1. Join mdb/dpanel-local-dev-policy and mdb/chrome-enterprise-debug-access. You must be part of these groups for anything to work. It may take a day or two to be approved.

  2. Follow the instructions here to create a new domain. In the process of following those instructions, an admin account for the domain will be created. You can think of the domain as the organization that an admin will apply policies to.

  3. Add the domain to the allow list shown here. It may take a day or two for the allow list to be updated.

  4. Create a new g4d workspace.

  5. Run the following command:

    boq run --node=java/com/google/chrome/cros/boq/dpanel/data/networks/service,java/com/google/chrome/cros/boq/dpanel/ui

    Note that there should not be any spaces separating the nodes, only commas. The command doesn't work if there are spaces.

    Also note that there is also a script to start nodes that may be easier to use. go/dpanel-getting-started#start-script The script will start bequt by default.

  6. Visit the following pages (preferably incognito mode), noting that if you are running from a cloudtop, replace with your cloudtop's hostname:

    • DpanelChromeUiServer for networks:
      • You should login to the dpanel with the admin account you created as part of step 1.
      • Make sure to use the full URL listed above, as you may get an error 404 if trying to access just the root '/'!
    • Backend Query Tool (BEQuT):
    • Hexa web console:

    Note that any UI changes you make should reflect automatically without having to re-reun the command, but sometimes you may have to re-run the command if the localhost gets in a bad state.

    If using a ChromeOS device to access the local server, use incognito mode and make sure to enable Beyond Corp extension in incognito mode.

Dpanel RPC studio instructions

Note that the following instructions assumes you've completed the steps to build a local instance of the Network Admin Dpanel. This section describes how you can verify fetching and updating protos (new or existing) by sending traffic to the Dpanel data node.

  1. You need an owned test account. Go to go/dev-test-account-conversion. Fill out the form like so using the admin account of the domain you created previously in the "Accounts" field.

  2. Start dpanel locally with that boq run command go/dpanel-getting-started#running-locally.

  3. Start rpc studios go/local-rpcstudio. Navigate to the url that is printed to the console.

  4. You should see your local networks service in the list of targets.

  5. Select whatever method you want - e.g. GetNetworkPolicy or UpdateNetworkPolicy

  6. Go to end user credentials. Turn on advanced mode. Select Test Gaia OTA. Should look like this.

  7. Craft the request. It is probably easiest to start from a real network request and edit from there. Here is how you can get details of a real UpdateNetworkPolicy request from boq-studio/

    1. Go to your local dpanel instance, and save a network.
    2. Go to boq-studio/. You should see your local instance. Click on it.
    3. Search the outgoing requests. Click on the outgoing request you want to copy. And copy the request.
    4. Go back to rpc studio. Select the text proto tab, and paste the request.
    5. Select the editor tab, and make your modifications.
  8. You should be ready to send the rpc now.

  9. You can see the request and response in rpc studio. If you want to debug the code. You can do so with ciderd go/cider-user-guide/debugging. See the section about attaching to a running process go/cider-user-guide/debugging#attaching-to-running-processes to attach to your local dpanel instance. This will allow you to trigger breakpoints in cider when you send your rpcs from rpc studio.

Log regeneration after proto changes

After modifying DPanel protos (e.g this CL, you may have to regenerate test logs in order to submit the CL. Otherwise, many of the tests will fail. Make sure to be in the cider workspace where your proto changes are, and use one of following methods to regnerate the logs:

Method 1

/google/data/ro/teams/frameworks-test-team/rpcreplay-cli/live/rpcreplay regen \

Method 2

guitar run --cluster=gem-ui-integration -w=//javatests/com/google/ccc/hosted/devicemanagement/emm/adminconsole/policy/service:guitar_borg_workflow  --version=citc:LOCAL

After the above command completes, a "sponge_invocation_id" should be generated. Use it in the following command:

/google/bin/releases/dasher-engprod/tools/regenerate_rpc_logs/regenerate_rpc_logs \

Method 3

blaze test --notest_loasd --test_strategy=local \

After the above command completes, a "sponge_invocation_id" should be generated. Use it in the following command:

/google/bin/releases/dasher-engprod/tools/regenerate_rpc_logs/regenerate_rpc_logs \


Debugging RPC calls on DPanel

In DPanel, you can use Sherlog a cross-stack event tracing service, to find out what is being passed in an RPC call. It collects data for debugging functional defects.