Skip to content

Commit f9872f0

Browse files
authored
Merge pull request #3657 from MicrosoftDocs/master-jdaly-customapi
Master jdaly customapi
2 parents 28607ac + ca7c382 commit f9872f0

22 files changed

+1319
-129
lines changed

powerapps-docs/developer/common-data-service/TOC.yml

Lines changed: 13 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -14,8 +14,20 @@
1414
href: webapi/index.md
1515
- name: Use Organization Service
1616
href: org-service/index.md
17-
- name: Create your own actions
17+
- name: Create your own messages
1818
href: custom-actions.md
19+
items:
20+
- name: Use Workflow Custom Actions with code
21+
href: workflow-custom-actions.md
22+
- name: Create and use Custom APIs (Preview)
23+
href: custom-api.md
24+
items:
25+
- name: Create a Custom API in the maker portal (Preview)
26+
href: create-custom-api-maker-portal.md
27+
- name: Create a Custom API with code (Preview)
28+
href: create-custom-api-with-code.md
29+
- name: Create a Custom API with solution files (Preview)
30+
href: create-custom-api-solution.md
1931
- name: Use FetchXML to query data
2032
href: use-fetchxml-construct-query.md
2133
items:

powerapps-docs/developer/common-data-service/create-custom-api-maker-portal.md

Lines changed: 308 additions & 0 deletions
Large diffs are not rendered by default.
Lines changed: 243 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,243 @@
1+
---
2+
title: "Create a Custom API with solution files (Common Data Service) | Microsoft Docs" # Intent and product brand in a unique string of 43-59 chars including spaces
3+
description: "You can write create custom APis by editing solution files." # 115-145 characters including spaces. This abstract displays in the search result.
4+
ms.custom: ""
5+
ms.date: 10/26/2020
6+
ms.reviewer: "pehecke"
7+
ms.service: powerapps
8+
ms.topic: "article"
9+
author: "JimDaly" # GitHub ID
10+
ms.author: "jdaly" # MSFT alias of Microsoft employees only
11+
manager: "ryjones" # MSFT alias of manager or PM counterpart
12+
search.audienceType:
13+
- developer
14+
search.app:
15+
- PowerApps
16+
- D365CE
17+
---
18+
# Create a Custom API with solution files
19+
20+
21+
[This topic is pre-release documentation and is subject to change.]
22+
23+
> [!NOTE]
24+
> This is an advanced topic that assumes you have already read and understood these topics:
25+
> - [Create and use Custom APIs](custom-api.md)
26+
> - [Create a Custom API in the maker portal](create-custom-api-maker-portal.md)
27+
28+
29+
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).
30+
31+
A solution file is a compressed (zip) file that has been exported from a Common Data Service 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.
32+
33+
> [!NOTE]
34+
> 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.
35+
36+
## Step 1: Create an Unmanaged solution
37+
38+
You should not try to compose a solution file manually. Use the tools in [Power Apps](https://make.powerapps.com/?utm_source=padocs&utm_medium=linkinadoc&utm_campaign=referralsfromdoc) 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.
39+
40+
1. [Create a solution](../../maker/common-data-service/create-solution.md)
41+
42+
For this example, the solution is defined simply like this:
43+
44+
:::image type="content" source="media/custom-api-solution.png" alt-text="An empty solution":::
45+
46+
1. [Export solutions](../../maker/common-data-service/export-solutions.md)
47+
48+
For this example, make sure you export an unmanaged solution. Managed solution is the default.
49+
50+
:::image type="content" source="media/export-empty-unmanaged-solution.png" alt-text="Option to select to export an unmanaged solution":::
51+
52+
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`.
53+
54+
## Step 2: Extract the contents of the solution and update the version
55+
56+
The solution is a compressed (zip) file.
57+
58+
1. Right-click on the file and choose **Extract All...** from the context menu.
59+
60+
You should see just the following three files in the folder:
61+
62+
- `[Content_Types].xml`
63+
- `customizations.xml`
64+
- `solution.xml`
65+
66+
1. Open the solution.xml file and locate the `Version` element.
67+
68+
```xml
69+
<ImportExportXml version="9.1.0.23474" SolutionPackageVersion="9.1" languagecode="1033" generatedBy="CrmLive" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance">
70+
<SolutionManifest>
71+
<UniqueName>CustomAPIExample</UniqueName>
72+
<LocalizedNames>
73+
<LocalizedName description="Custom API Example" languagecode="1033" />
74+
</LocalizedNames>
75+
<Descriptions />
76+
<Version>1.0.0.1</Version>
77+
```
78+
79+
1. Update the value by 1. In this example, it will be `<Version>1.0.0.2</Version>`.
80+
1. Save the file.
81+
82+
## Step 3: Add the definition of the Custom API
83+
84+
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.
85+
Within the folder, the data representing the Custom API is found within an XML file named `customapi.xml`
86+
87+
1. In the folder with the extracted files, create a new folder named `customapis`.
88+
1. In the **customapis** folder, create a folder with the `UniqueName` of the Custom API you want to create. For this example we will use `sample_CustomAPIExample`.
89+
1. In the **sample_CustomAPIExample** folder you created, create a file named `customapi.xml`.
90+
1. Edit the customapi.xml to set the properties of the custom API you want to create. For this example, we will use the following:
91+
```xml
92+
<customapi uniquename="sample_CustomAPIExample">
93+
<allowedcustomprocessingsteptype>0</allowedcustomprocessingsteptype>
94+
<bindingtype>0</bindingtype>
95+
<boundentitylogicalname />
96+
<description default="A simple example of a Custom API">
97+
<label description="A simple example of a Custom API" languagecode="1033" />
98+
</description>
99+
<displayname default="Custom API Example">
100+
<label description="Custom API Example" languagecode="1033" />
101+
</displayname>
102+
<executeprivilegename />
103+
<isfunction>0</isfunction>
104+
<isprivate>0</isprivate>
105+
<name>sample_CustomAPIExample</name>
106+
<plugintypeid />
107+
</customapi>
108+
```
109+
110+
See the information in [CustomAPI entity attributes](custom-api.md#customapi-entity-attributes) to set the values of the elements.
111+
112+
> [!NOTE]
113+
> 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:
114+
>
115+
> ```xml
116+
> <plugintypeid>
117+
> <plugintypeid>{Add the GUID value of the plug-in type id}</plugintypeid>
118+
> </plugintypeid>
119+
> ```
120+
>
121+
> 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:
122+
>
123+
> ```http
124+
> GET https://yourorg.crm.dynamics.com/api/data/v9.1/plugintypes?$select=name&$filter=contains(name,'MyPlugin.TypeName')
125+
> ```
126+
127+
## Step 4: Add any Custom API Request Parameters
128+
129+
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.
130+
131+
1. 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`.
132+
1. 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 use `StringParameter`.
133+
1. Within the folder, add an xml file named `customapirequestparameter.xml`.
134+
1. 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:
135+
136+
```xml
137+
<customapirequestparameter uniquename="StringParameter">
138+
<description default="The StringParameter request parameter for Custom API Example">
139+
<label description="The StringParameter request parameter for Custom API Example" languagecode="1033" />
140+
</description>
141+
<displayname default="Custom API Example String Parameter">
142+
<label description="Custom API Example String Parameter" languagecode="1033" />
143+
</displayname>
144+
<isoptional>0</isoptional>
145+
<logicalentityname />
146+
<name>sample_CustomAPIExample.StringParameter</name>
147+
<type>10</type>
148+
</customapirequestparameter>
149+
```
150+
151+
See the information in [CustomAPIRequestParameter entity attributes](custom-api.md#customapirequestparameter-entity-attributes) to set the values of the elements.
152+
153+
154+
## Step 5: Add any Custom API Response Properties
155+
156+
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.
157+
158+
1. 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](#step-3-add-the-definition-of-the-custom-api), create a folder named `customapiresponseproperties`.
159+
1. 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 use `StringProperty`.
160+
1. Within the folder, add an xml file named `customapiresponseproperty.xml`.
161+
1. 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:
162+
163+
```xml
164+
<customapiresponseproperty uniquename="StringProperty">
165+
<description default="The StringProperty response property for Custom API Example">
166+
<label description="The StringProperty response property for Custom API Example" languagecode="1033" />
167+
</description>
168+
<displayname default="Custom API Example String Property">
169+
<label description="Custom API Example String Property" languagecode="1033" />
170+
</displayname>
171+
<logicalentityname />
172+
<name>sample_CustomAPIExample.StringProperty</name>
173+
<type>10</type>
174+
</customapiresponseproperty>
175+
```
176+
177+
See the information in [CustomAPIResponseProperty entity attributes](custom-api.md#customapiresponseproperty-entity-attributes) to set the values of the elements.
178+
179+
> [!NOTE]
180+
> 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.
181+
182+
## Step 6: Compress the files to create a new solution file
183+
184+
1. Return to the folder where you extracted the original solution file in [Step 2: Extract the contents of the solution and update the version](#step-2-extract-the-contents-of-the-solution-and-update-the-version)
185+
1. Select all the extracted files and the **customapis** folder you created.
186+
187+
:::image type="content" source="media/selected-solution-files.png" alt-text="The selected solution files":::
188+
189+
1. Right-click the selected files and choose **Send to** > **Compressed (zipped folder)**.
190+
1. 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`.
191+
192+
## Step 7: Import the solution with the definition of your Custom API
193+
194+
1. Return to [Power Apps](https://make.powerapps.com/?utm_source=padocs&utm_medium=linkinadoc&utm_campaign=referralsfromdoc) and select **Solutions**.
195+
1. Select **Import** and follow the instructions to select the solution file you created in the previous step.
196+
197+
:::image type="content" source="media/import-solution-with-customapi.png" alt-text="Import the solution file":::
198+
199+
> [!NOTE]
200+
> 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](#step-2-extract-the-contents-of-the-solution-and-update-the-version).
201+
202+
1. You should see a warning saying **This solution package contains an update for a solution that is already installed**. Click **Import** to continue.
203+
1. Wait a few minutes while the solution import completes.
204+
205+
> [!NOTE]
206+
> 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](https://support.microsoft.com/help/4343228/the-solution-installation-or-removal-failed-due-to-the-installation-or)
207+
208+
## Step 8: Verify that the Custom API was added to your solution
209+
210+
Open the solution you created and verify that the Custom API and the associated request parameters and response properties are included.
211+
212+
:::image type="content" source="media/customapi-solution-installed-successfully.png" alt-text="Showing that the solution component installed successfully":::
213+
214+
At this point, you can test your API using the steps describe in [Test your Custom API](create-custom-api-maker-portal.md#test-your-custom-api)
215+
216+
217+
## Providing Localized Labels with the solution
218+
219+
As an alternative to using the process described in [Localized values](custom-api.md#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
220+
221+
```xml
222+
<customapi uniquename="sample_CustomAPIExample">
223+
<allowedcustomprocessingsteptype>0</allowedcustomprocessingsteptype>
224+
<bindingtype>0</bindingtype>
225+
<description default="A simple example of a Custom API">
226+
<label description="A simple example of a Custom API" languagecode="1033" />
227+
<label description="カスタムAPIの簡単な例" languagecode="1041" />
228+
</description>
229+
<displayname default="Custom API Example">
230+
<label description="Custom API Example" languagecode="1033" />
231+
<label description="カスタムAPIの例" languagecode="1041" />
232+
</displayname>
233+
<isfunction>0</isfunction>
234+
<name>sample_CustomAPIExample</name>
235+
</customapi>
236+
```
237+
238+
### See also
239+
240+
[Create and use Custom APIs](custom-api.md)<br />
241+
[Create a Custom API in the maker portal](create-custom-api-maker-portal.md)<br />
242+
[Create a Custom API with code](create-custom-api-with-code.md)<br />
243+
[Create your own messages](custom-actions.md)<br />

0 commit comments

Comments
 (0)