Easily Access Environment Variables with the Power Platform

A quick recap on environment variables

Environment variables in Model-Driven Power Apps were introduced in November 2019.  As of September 2020, they are still in Preview mode.  Their purpose is to allow solution designers a place to specify environment-specific values that they can define and reference at runtime. 

For example, if you have a Flow that needs to send an email with a link to a specific record, you probably want to include the appId in the URL for that record.  By using environment variables, you can avoid editing the flow in each environment you deploy it to (dev, test, and production).  While you will still need to assign the environment variable a value in each environment, you won’t need to do that every time you deploy the flow.

Environment variables are made up of two entities: Environment Variable Definitions and Environment Variable Values.  What makes them special is that you can add specific instances of those entities to Solutions.  At Root16, we typically only embed the Environment Variable Definition in a solution and create the related Environment Variable Value in each target environment.

Let’s explore what makes up the two entities in the following sections.

Environment Variable Definition

When you choose to add a new environment variable to a solution, you are presented with a form that prompts for the following values:

  • Display name – The human-readable name.
  • Name – The unique name that will be used by flow or API calls to look up the variable.  This is also called the “schema name” in the API.
  • Description (optional) – A good place to describe what the variable is used for.
  • Data Type – Possible values of (Decimal number, JSON, Text or Two options).
  • Default Value – Shows up after you select a Data Type.  You can leave this blank or specify a default value.  If you are going to have a different value in each environment, just leave this blank.  If a common value is shared across several environments, you can populate the default.

Environment Variable Value

You will also see a prompt at the end of the Environment Variable Definition form where you can specify the Current Value for your new environment variable.  We typically avoid filling this out here as it will include your Environment Variable Value in the solution that gets deployed.  Instead, when you save the variable definition you should see a warning at the top of your browser that you have an environment variable without a value.  Click that warning and fill out the value in the new form that pops up.  This will create the same Environment Variable Value entity, but it won’t be included in your solution.

Reading Environment Variables

Once you have your variables set up, you’ll want to access them from places like Flows and JavaScript.  Typically you want to check for both a value and the default value and a value will “win” if both are specified.  Let’s take a look at how to implement this in a few examples.

Reading from an on demand Flow

In the future, Microsoft could well enhance the Common Data Service connector to have an out of the box “Get Environment Variable Value” action, but today we need to use the “List records” action and a few expressions to access them efficiently.

In order to make environment variable access easier across the organization, we like to set up an on-demand flow that can be called from other flows.  This also provides us with a layer of abstraction so that later if Microsoft does simplify the reading of environment variables, we can just update this on-demand flow instead of all the flows that are reading environment variables.

Our on-demand flow looks like this:

Here is the breakdown of the trigger and actions:

  • Manually trigger a flow – This trigger is one of the ways you can make your flow callable from other flows.
    • Inputs – Add one required input called “Schema Name” that Flow designers can pass in when they run this Flow.
  • List records for an entity – This CDS action allows us to query for our environment variable.  The following actions assume this action is named “GetEnvVarDef”.
    • Entity Name – Environment Variable Definitions
    • Select Query – defaultvalue
      Specifying which attributes we want returned will reduce the size of our query results.
    • Filter Query – schemaname eq ‘Schema Name’
      Schema Name is a dynamic value referencing the trigger input we added.
    • Expand Query – environmentvariabledefinition_environmentvariablevalue($select=value)
      This will return any related Environment Variable Values along with the Definition in a single call.  We also trim down the related attributes to only include the one named “value”.  Smaller payloads for faster calls.
    • Top Count – 1
      Limit the response to a single result.
  • Initialize a variable – The first variable holds the default value of the env variable.  Splitting up the response into a few Flow variables make the expressions easier to read/maintain.
    • Name – defaultValue
    • Type – String
    • Value – first(outputs(‘GetEnvVarDef’)?[‘body/value’])?[‘defaultvalue’]
      Get the first response from our List records action and then looks for the “defaultvalue” property on that record.
  • Initialize a variable – The second variable holds the value if it exists in the related entity.
    • Name – value
    • Type – String
    • Value – first(first(outputs(‘GetEnvVarDef’)?[‘body/value’])?[‘environmentvariabledefinition_environmentvariablevalue’])?[‘value’]
      Gets the first result from the List records action, then gets the first item in the array property that contains the values.
  • Respond to PowerApp or flow – This is how we pass the value back to the calling Flow.
    • Outputs – Add an output named Value and set it to if(empty(variables(‘value’)), variables(‘defaultValue’), variables(‘value’))
      This will be the value or the defaultValue if the value is null/blank.

Some of the expressions were a mouthful there and you can see why you wouldn’t want to copy those around in multiple flows.  The nice thing is that now that we have done this work once, we can call this from other flows fairly easily:

In this case, you can just use a Run another Flow from this Flow action.  You can see the Schema Name input where you specify the schema name of the environment variable you defined.  In later actions, you can reference the Value output as dynamic content.

Reading from JavaScript

In addition to Flows, you might find yourself wanting to read environment variable values from JavaScript.  Perhaps you want to look up an external API URL or trigger a Flow via an HTTP POST and need the URL.  In this case we can follow very similar logic to our Flow:

async function getEnvironmentVariableValue (schemaName) {
   var response = await Xrm.WebApi.retrieveMultipleRecords(
       'environmentvariabledefinition', 
       [
           "?$select=defaultvalue",
           "&$filter=schemaname eq '", schemaName, "'",
           "&$expand=environmentvariabledefinition_environmentvariablevalue($select=value)"
       ].join('')
   );

   var value = null;

    if (response.entities.length == 1) {
       if (response.entities[0].environmentvariabledefinition_environmentvariablevalue.length == 1) {
           value = response.entities[0].environmentvariabledefinition_environmentvariablevalue[0].value;
       }
       else {
           value = response.entities[0].defaultvalue;
       }
   }

return value;
}

Final Thoughts

While it might take a few steps to get environment variables set up and then read them, in the end its worth the extra time as it will allow you to write generic extensions to Power Apps that don’t have environment-specific details hard-coded into them.  This allows you to embrace build automation and push your solutions from environment to environment with fewer manual steps required.

For more details on environment variables visit: Use environment variables in solutions – Power Apps.

One thought on “Easily Access Environment Variables with the Power Platform

  1. I have to thank you for
    the efforts you’ve put in penning this site.
    I am hoping to view
    the same high-grade blog posts from you
    in the future as well. In fact, your creative writing
    abilities has inspired me to get my own site now

Comments are closed.