Add missing docs for humanitec app connection endpoints

This commit is contained in:
carlosmonastyrski
2025-03-13 15:50:32 -03:00
parent 1d14cdf334
commit f15e61dbd9
15 changed files with 135 additions and 44 deletions
@@ -84,21 +84,17 @@ export const listOrganizations = async (appConnection: THumanitecConnection): Pr
} }
); );
if (!appsResponse.data) { if (appsResponse.data) {
throw new InternalServerError({ const apps = appsResponse.data;
message: "Failed to get apps for organization: Response was empty" orgsWithApps.push({
...org,
apps: apps.map((app) => ({
name: app.name,
id: app.id,
envs: app.envs
}))
}); });
} }
const apps = appsResponse.data;
orgsWithApps.push({
...org,
apps: apps.map((app) => ({
name: app.name,
id: app.id,
envs: app.envs
}))
});
} catch (error) { } catch (error) {
logger.error(error, `Failed to get apps for organization ${org.name}`); logger.error(error, `Failed to get apps for organization ${org.name}`);
} }
@@ -15,26 +15,20 @@ const getHumanitecSecrets = async (secretSync: THumanitecSyncWithCredentials) =>
} }
} = secretSync; } = secretSync;
try { let url = `${IntegrationUrls.HUMANITEC_API_URL}/orgs/${destinationConfig.org}/apps/${destinationConfig.app}`;
let url = `${IntegrationUrls.HUMANITEC_API_URL}/orgs/${destinationConfig.org}/apps/${destinationConfig.app}`; if (destinationConfig.scope === HumanitecSyncScope.Environment) {
if (destinationConfig.scope === HumanitecSyncScope.Environment) { url += `/envs/${destinationConfig.env}`;
url += `/envs/${destinationConfig.env}`;
}
url += "/values";
const { data } = await request.get<HumanitecSecret[]>(url, {
headers: {
Authorization: `Bearer ${apiToken}`,
"Accept-Encoding": "application/json"
}
});
return data;
} catch (error) {
throw new SecretSyncError({
error
});
} }
url += "/values";
const { data } = await request.get<HumanitecSecret[]>(url, {
headers: {
Authorization: `Bearer ${apiToken}`,
"Accept-Encoding": "application/json"
}
});
return data;
}; };
const deleteSecret = async (secretSync: THumanitecSyncWithCredentials, encryptedSecret: HumanitecSecret) => { const deleteSecret = async (secretSync: THumanitecSyncWithCredentials, encryptedSecret: HumanitecSecret) => {
@@ -0,0 +1,4 @@
---
title: "Available"
openapi: "GET /api/v1/app-connections/humanitec/available"
---
@@ -0,0 +1,10 @@
---
title: "Create"
openapi: "POST /api/v1/app-connections/humanitec"
---
<Note>
Humanitec Connections must be created through the Infisical UI.
Check out the configuration docs for [Humanitec Connections](/integrations/app-connections/humanitec) for a step-by-step
guide.
</Note>
@@ -0,0 +1,4 @@
---
title: "Delete"
openapi: "DELETE /api/v1/app-connections/humanitec/{connectionId}"
---
@@ -0,0 +1,4 @@
---
title: "Get by ID"
openapi: "GET /api/v1/app-connections/humanitec/{connectionId}"
---
@@ -0,0 +1,4 @@
---
title: "Get by Name"
openapi: "GET /api/v1/app-connections/humanitec/connection-name/{connectionName}"
---
@@ -0,0 +1,4 @@
---
title: "List"
openapi: "GET /api/v1/app-connections/humanitec"
---
@@ -0,0 +1,10 @@
---
title: "Update"
openapi: "PATCH /api/v1/app-connections/humanitec/{connectionId}"
---
<Note>
Humanitec Connections must be updated through the Infisical UI.
Check out the configuration docs for [Humanitec Connections](/integrations/app-connections/humanitec) for a step-by-step
guide.
</Note>
Binary file not shown.

Before

Width:  |  Height:  |  Size: 269 KiB

After

Width:  |  Height:  |  Size: 267 KiB

@@ -9,7 +9,7 @@ Infisical supports connecting to Humanitec using a service user.
<Steps> <Steps>
<Step title="Move to Service Users on Humanitec"> <Step title="Move to Service Users on Humanitec">
Navigate to the Humanitec Service Users tab. Navigate to the Humanitec **Service Users** tab.
![Humanitec Service Users Tab](/images/app-connections/humanitec/humanitec-service-users.png) ![Humanitec Service Users Tab](/images/app-connections/humanitec/humanitec-service-users.png)
</Step> </Step>
<Step title="Create a Service User"> <Step title="Create a Service User">
@@ -21,25 +21,26 @@ Infisical supports connecting to Humanitec using a service user.
![Humanitec Add API Token](/images/app-connections/humanitec/humanitec-add-api-token.png) ![Humanitec Add API Token](/images/app-connections/humanitec/humanitec-add-api-token.png)
</Step> </Step>
<Step title="Create the API Token for the Service User"> <Step title="Create the API Token for the Service User">
Create the API token for the service user. Depending on the expiry date set, the token will expire and this integration will stop working. Create the API token for the service user.
If you configure an expiry date for your API token you will need to manually rotate to a new token prior to expiration to avoid integration downtime.
This token's permission will be limited to the **Service User** role. This token's permission will be limited to the **Service User** role.
![Humanitec Create API Token](/images/app-connections/humanitec/humanitec-create-api-token.png) ![Humanitec Create API Token](/images/app-connections/humanitec/humanitec-create-api-token.png)
</Step> </Step>
<Step title="Copy the API Token"> <Step title="Copy the API Token">
A modal with the API token will be displayed. Copy the token and save it in a secure location. A modal with the API token will be displayed. Save the token in a secure location for later use in the following steps.
![Humanitec Copy API Token](/images/app-connections/humanitec/humanitec-copy-api-token.png) ![Humanitec Copy API Token](/images/app-connections/humanitec/humanitec-copy-api-token.png)
</Step> </Step>
<Step title="Service User has been successfully created"> <Step title="Service User has been successfully created">
After following the previous steps the Service User has been successfully created. And now should be visible on the Service Users tab. After following the previous steps the Service User has been successfully created, and now should be visible on the Service Users tab.
![Humanitec Service User Created](/images/app-connections/humanitec/humanitec-service-account-filled.png) ![Humanitec Service User Created](/images/app-connections/humanitec/humanitec-service-account-filled.png)
</Step> </Step>
<Step title="Add Service User to Application"> <Step title="Add Service User to Application">
Move to Appplication Tab and add the Service User to the Application you want to sync with Infisical. Move to the **Applications** tab and add the Service User to the Application you want to sync with Infisical.
Clicking on the App Title will open the App details page. Clicking on the App Title will open the App details page.
![Humanitec Applications Tab](/images/app-connections/humanitec/humanitec-applications-tab.png) ![Humanitec Applications Tab](/images/app-connections/humanitec/humanitec-applications-tab.png)
</Step> </Step>
<Step title="Add new member to this Application"> <Step title="Add new member to this Application">
Move to the People tab and add a new member to this Application. The recently created User Service should be visible on the dropdown shown. Move to the **People** tab and add a new member to this Application. The recently created User Service should be visible on the dropdown shown.
Make sure to assign at least Developer role as Write permissions are required. Make sure to assign at least Developer role as Write permissions are required.
![Humanitec Add User to Application](/images/app-connections/humanitec/humanitec-add-user.png) ![Humanitec Add User to Application](/images/app-connections/humanitec/humanitec-add-user.png)
![Humanitec Add User Options](/images/app-connections/humanitec/humanitec-add-user-options.png) ![Humanitec Add User Options](/images/app-connections/humanitec/humanitec-add-user-options.png)
+2 -2
View File
@@ -129,8 +129,8 @@ description: "Learn how to configure a Humanitec Sync for Infisical."
}, },
"projectId": "3c90c3cc-0d44-4b50-8888-8dd25736052a", "projectId": "3c90c3cc-0d44-4b50-8888-8dd25736052a",
"connection": { "connection": {
"app": "github", "app": "humanitec",
"name": "my-github-connection", "name": "my-humanitec-connection",
"id": "3c90c3cc-0d44-4b50-8888-8dd25736052a" "id": "3c90c3cc-0d44-4b50-8888-8dd25736052a"
}, },
"environment": { "environment": {
+12
View File
@@ -900,6 +900,18 @@
"api-reference/endpoints/app-connections/github/update", "api-reference/endpoints/app-connections/github/update",
"api-reference/endpoints/app-connections/github/delete" "api-reference/endpoints/app-connections/github/delete"
] ]
},
{
"group": "Humanitec",
"pages": [
"api-reference/endpoints/app-connections/humanitec/list",
"api-reference/endpoints/app-connections/humanitec/available",
"api-reference/endpoints/app-connections/humanitec/get-by-id",
"api-reference/endpoints/app-connections/humanitec/get-by-name",
"api-reference/endpoints/app-connections/humanitec/create",
"api-reference/endpoints/app-connections/humanitec/update",
"api-reference/endpoints/app-connections/humanitec/delete"
]
} }
] ]
}, },
@@ -5,6 +5,7 @@ import { FontAwesomeIcon } from "@fortawesome/react-fontawesome";
import { SecretSyncConnectionField } from "@app/components/secret-syncs/forms/SecretSyncConnectionField"; import { SecretSyncConnectionField } from "@app/components/secret-syncs/forms/SecretSyncConnectionField";
import { FilterableSelect, FormControl, Select, SelectItem, Tooltip } from "@app/components/v2"; import { FilterableSelect, FormControl, Select, SelectItem, Tooltip } from "@app/components/v2";
import { HUMANITEC_SYNC_SCOPES } from "@app/helpers/secretSyncs";
import { import {
THumanitecConnectionApp, THumanitecConnectionApp,
THumanitecConnectionEnvironment, THumanitecConnectionEnvironment,
@@ -41,6 +42,7 @@ export const HumanitecSyncFields = () => {
onChange={() => { onChange={() => {
setValue("destinationConfig.org", ""); setValue("destinationConfig.org", "");
setValue("destinationConfig.app", ""); setValue("destinationConfig.app", "");
setValue("destinationConfig.env", "");
}} }}
/> />
<Controller <Controller
@@ -48,11 +50,38 @@ export const HumanitecSyncFields = () => {
control={control} control={control}
defaultValue={HumanitecSyncScope.Application} defaultValue={HumanitecSyncScope.Application}
render={({ field: { value, onChange }, fieldState: { error } }) => ( render={({ field: { value, onChange }, fieldState: { error } }) => (
<FormControl errorText={error?.message} isError={Boolean(error?.message)} label="Scope"> <FormControl
errorText={error?.message}
isError={Boolean(error?.message)}
label="Scope"
tooltipClassName="max-w-lg py-3"
tooltipText={
<div className="flex flex-col gap-3">
<p>
Specify how Infisical should manage secrets from Humanitec. The following options
are available:
</p>
<ul className="flex list-disc flex-col gap-3 pl-4">
{Object.values(HUMANITEC_SYNC_SCOPES).map(({ name, description }) => {
return (
<li key={name}>
<p className="text-mineshaft-300">
<span className="font-medium text-bunker-200">{name}</span>: {description}
</p>
</li>
);
})}
</ul>
</div>
}
>
<Select <Select
value={value} value={value}
onValueChange={(val) => { onValueChange={(val) => {
onChange(val); onChange(val);
setValue("destinationConfig.env", "");
setValue("destinationConfig.app", "");
setValue("destinationConfig.org", "");
}} }}
className="w-full border border-mineshaft-500 capitalize" className="w-full border border-mineshaft-500 capitalize"
position="popper" position="popper"
@@ -81,9 +110,11 @@ export const HumanitecSyncFields = () => {
isLoading={isOrganizationsPending && Boolean(connectionId)} isLoading={isOrganizationsPending && Boolean(connectionId)}
isDisabled={!connectionId} isDisabled={!connectionId}
value={organizations ? (organizations.find((org) => org.id === value) ?? []) : []} value={organizations ? (organizations.find((org) => org.id === value) ?? []) : []}
onChange={(option) => onChange={(option) => {
onChange((option as SingleValue<THumanitecConnectionOrganization>)?.id ?? null) onChange((option as SingleValue<THumanitecConnectionOrganization>)?.id ?? null);
} setValue("destinationConfig.app", "");
setValue("destinationConfig.env", "");
}}
options={organizations} options={organizations}
placeholder="Select an organization..." placeholder="Select an organization..."
getOptionLabel={(option) => option.name} getOptionLabel={(option) => option.name}
+17
View File
@@ -4,6 +4,7 @@ import {
SecretSyncImportBehavior, SecretSyncImportBehavior,
SecretSyncInitialSyncBehavior SecretSyncInitialSyncBehavior
} from "@app/hooks/api/secretSyncs"; } from "@app/hooks/api/secretSyncs";
import { HumanitecSyncScope } from "@app/hooks/api/secretSyncs/types/humanitec-sync";
export const SECRET_SYNC_MAP: Record<SecretSync, { name: string; image: string }> = { export const SECRET_SYNC_MAP: Record<SecretSync, { name: string; image: string }> = {
[SecretSync.AWSParameterStore]: { name: "AWS Parameter Store", image: "Amazon Web Services.png" }, [SecretSync.AWSParameterStore]: { name: "AWS Parameter Store", image: "Amazon Web Services.png" },
@@ -67,3 +68,19 @@ export const SECRET_SYNC_IMPORT_BEHAVIOR_MAP: Record<
description: `Infisical will import any secrets present in the ${destinationName} destination, prioritizing values from ${destinationName} over Infisical when keys conflict.` description: `Infisical will import any secrets present in the ${destinationName} destination, prioritizing values from ${destinationName} over Infisical when keys conflict.`
}) })
}; };
export const HUMANITEC_SYNC_SCOPES: Record<
HumanitecSyncScope,
{ name: string; description: string }
> = {
[HumanitecSyncScope.Application]: {
name: "Application",
description:
"Infisical will import any secrets present in the selected Humanitec application. This includes all secrets that are not limited to a specific environment."
},
[HumanitecSyncScope.Environment]: {
name: "Environment",
description:
"Infisical will import any secrets present in the selected Humanitec environment. This includes all secrets that are limited to the selected environment."
}
};