Create a Custom API with solution files
[This topic is pre-release documentation and is subject to change.]
Note
This is an advanced topic that assumes you have already read and understood these topics:
While you can create Custom APIs through a designer or with code, you can also define them by working with files within a solution. This may be the preferred option for solution publishers who apply the recommended best practices for Application Lifecycle Management (ALM).
A solution file is a compressed (zip) file that has been exported from a Microsoft Dataverse instance. The contents of this file can be extracted and the components checked into a source repository. The contents can be edited and then compressed again. The changes applied to the solution will then be part of the solution and will be created when the solution is imported.
Note
These processes are typically automated with tools and processes that are beyond the scope of this topic. This topic will focus on the simple scenario of creating a Custom API by manually manipulating the extracted files in a solution to demonstrate how the data in the files can be used to create Custom API.
Step 1: Create an Unmanaged solution
You should not try to compose a solution file manually. Use the tools in Power Apps to generate a solution file. Use the steps in the following topics to create and export a solution. The solution doesn't need to contain any solution components.
-
For this example, the solution is defined simply like this:
-
For this example, make sure you export an unmanaged solution. Managed solution is the default.
You can find the exported file in your downloads folder. It will have a name that depends on the name and version of the solution, in this case: CustomAPIExample_1_0_0_2.zip
.
Step 2: Extract the contents of the solution and update the version
The solution is a compressed (zip) file.
Right-click on the file and choose Extract All... from the context menu.
You should see just the following three files in the folder:
[Content_Types].xml
customizations.xml
solution.xml
Open the solution.xml file and locate the
Version
element.<ImportExportXml version="9.1.0.23474" SolutionPackageVersion="9.1" languagecode="1033" generatedBy="CrmLive" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"> <SolutionManifest> <UniqueName>CustomAPIExample</UniqueName> <LocalizedNames> <LocalizedName description="Custom API Example" languagecode="1033" /> </LocalizedNames> <Descriptions /> <Version>1.0.0.1</Version>
Update the value by 1. In this example, it will be
<Version>1.0.0.2</Version>
.Save the file.
Step 3: Add the definition of the Custom API
All Custom APIs in a solution are found within a folder named customapis. Within that folder each Custom API will be in a folder named after the Custom API UniqueName
property.
Within the folder, the data representing the Custom API is found within an XML file named customapi.xml
- In the folder with the extracted files, create a new folder named
customapis
. - In the customapis folder, create a folder with the
UniqueName
of the Custom API you want to create. For this example we will usesample_CustomAPIExample
. - In the sample_CustomAPIExample folder you created, create a file named
customapi.xml
. - Edit the customapi.xml to set the properties of the custom API you want to create. For this example, we will use the following:
<customapi uniquename="sample_CustomAPIExample"> <allowedcustomprocessingsteptype>0</allowedcustomprocessingsteptype> <bindingtype>0</bindingtype> <boundentitylogicalname /> <description default="A simple example of a Custom API"> <label description="A simple example of a Custom API" languagecode="1033" /> </description> <displayname default="Custom API Example"> <label description="Custom API Example" languagecode="1033" /> </displayname> <executeprivilegename /> <isfunction>0</isfunction> <isprivate>0</isprivate> <name>sample_CustomAPIExample</name> <plugintypeid /> </customapi>
See the information in CustomAPI entity attributes to set the values of the elements.
Note
If you already have a Plug-in Type that you want to associate with this Custom API, you can include a reference to it in this definition by adding the following element within the <customapi>
element:
<plugintypeid>
<plugintypeid>{Add the GUID value of the plug-in type id}</plugintypeid>
</plugintypeid>
You can retrieve the Plug-in Type Id using a Web API query like this where you know the name of the plug-in type:
GET https://yourorg.crm.dynamics.com/api/data/v9.1/plugintypes?$select=name&$filter=contains(name,'MyPlugin.TypeName')
Step 4: Add any Custom API Request Parameters
Any definitions of request parameters for the Custom API are included in a folder called customapirequestparameters
. Within that folder each Custom API Request Parameter will be in a folder named after the Custom API Request Parameter UniqueName
property.
- If your Custom API has an request parameters, within the folder for the Custom API you created in the previous step, create a folder named
customapirequestparameters
. - For each Custom API Request Parameter, create a new folder using the
UniqueName
property of the Custom API Request Parameter. For this example we will useStringParameter
. - Within the folder, add an xml file named
customapirequestparameter.xml
. - Edit the customapirequestparameter.xml file to set the properties of the Custom API you want to create. For this example, we will use the following:
<customapirequestparameter uniquename="StringParameter">
<description default="The StringParameter request parameter for Custom API Example">
<label description="The StringParameter request parameter for Custom API Example" languagecode="1033" />
</description>
<displayname default="Custom API Example String Parameter">
<label description="Custom API Example String Parameter" languagecode="1033" />
</displayname>
<isoptional>0</isoptional>
<logicalentityname />
<name>sample_CustomAPIExample.StringParameter</name>
<type>10</type>
</customapirequestparameter>
See the information in CustomAPIRequestParameter entity attributes to set the values of the elements.
Step 5: Add any Custom API Response Properties
Any definitions of response properties for the Custom API are included in a folder called customapiresponseproperties
. Within that folder each Custom API Response Property will be in a folder named after the Custom API Response Property UniqueName
property.
- If your Custom API has an response properties, within the folder for the Custom API you created in Step 3: Add the definition of the Custom API, create a folder named
customapiresponseproperties
. - For each Custom API Response Property, create a new folder using the
UniqueName
property of the Custom API Response Property. For this example we will useStringProperty
. - Within the folder, add an xml file named
customapiresponseproperty.xml
. - Edit the customapiresponseproperty.xml file to set the properties of the Custom API you want to create. For this example, we will use the following:
<customapiresponseproperty uniquename="StringProperty">
<description default="The StringProperty response property for Custom API Example">
<label description="The StringProperty response property for Custom API Example" languagecode="1033" />
</description>
<displayname default="Custom API Example String Property">
<label description="Custom API Example String Property" languagecode="1033" />
</displayname>
<logicalentityname />
<name>sample_CustomAPIExample.StringProperty</name>
<type>10</type>
</customapiresponseproperty>
See the information in CustomAPIResponseProperty entity attributes to set the values of the elements.
Note
While the schema for request parameters and response properties is very similar, note that isoptional
is not valid for a response property and will cause an error when you try to import the solution.
Step 6: Compress the files to create a new solution file
Return to the folder where you extracted the original solution file in Step 2: Extract the contents of the solution and update the version
Select all the extracted files and the customapis folder you created.
Right-click the selected files and choose Send to > Compressed (zipped folder).
You can re-name the resulting file to be anything you want. For this example, rename it to match the original exported solution file:
CustomAPIExample_1_0_0_2.zip
.
Step 7: Import the solution with the definition of your Custom API
Return to Power Apps and select Solutions.
Select Import and follow the instructions to select the solution file you created in the previous step.
Note
If you see a warning saying This version of the solution package is already installed, you must not have updated the
Version
element of the solution.xml as described in Step 2: Extract the contents of the solution and update the version.You should see a warning saying This solution package contains an update for a solution that is already installed. Click Import to continue.
Wait a few minutes while the solution import completes.
Note
It is possible you will see an error if another solution is being installed at the same time. More information: The solution installation or removal failed due to the installation or removal of another solution at the same time
Step 8: Verify that the Custom API was added to your solution
Open the solution you created and verify that the Custom API and the associated request parameters and response properties are included.
At this point, you can test your API using the steps describe in Test your Custom API
Providing Localized Labels with the solution
As an alternative to using the process described in Localized values, if you are editing the solution files for Custom API entities, you can provide translations directly in these files. For example if you want to provide Japanese localized labels for your Custom API, you can provide them for the description
and displayname
properties as shown below
<customapi uniquename="sample_CustomAPIExample">
<allowedcustomprocessingsteptype>0</allowedcustomprocessingsteptype>
<bindingtype>0</bindingtype>
<description default="A simple example of a Custom API">
<label description="A simple example of a Custom API" languagecode="1033" />
<label description="カスタムAPIの簡単な例" languagecode="1041" />
</description>
<displayname default="Custom API Example">
<label description="Custom API Example" languagecode="1033" />
<label description="カスタムAPIの例" languagecode="1041" />
</displayname>
<isfunction>0</isfunction>
<name>sample_CustomAPIExample</name>
</customapi>
See also
Create and use Custom APIs
Create a Custom API in the maker portal
Create a Custom API with code
Create your own messages