<@U04UQ68083H> What is the recommended way to dele...
# ory-copilot
g
@chilly-king-10285 What is the recommended way to delete identities?
c
A message from kapa.ai
The recommended way to delete identities in Ory is by using the
DELETE /admin/identities/{id}
endpoint of the Ory API. This endpoint irrecoverably and permanently deletes the identity given its ID. This action cannot be undone. The endpoint returns 204 when the identity was deleted or when the identity was not found, in which case it is assumed that it has been deleted already. Here is an example of how to delete an identity using the Go SDK:
Copy code
go r, err = apiClient.IdentityApi.DeleteIdentity(context.Background(), getIdentity.Id).Execute()   if err != nil {    fmt.Fprintf(os.Stderr, "Error when calling `IdentityApi.DeleteIdentity``: %v\n", err)    fmt.Fprintf(os.Stderr, "Full HTTP response: %v\n", r)   }   fmt.Println("Successfully Removed identity")
Please note that the ID of the identity to be deleted is required. For more information, you can refer to the [Ory API Reference](https://www.ory.sh/docs/reference/api) and the [Kratos API Reference](https://www.ory.sh/docs/kratos/reference/api).
g
How should I configure my kratos client to have the public and admin API available and how to switch between them?
@chilly-king-10285 How should I configure my kratos client to have the public and admin API available and how to switch between them?
c
A message from kapa.ai
To configure your Kratos client to have both the public and admin API available, you need to set up two separate API instances. Each instance should have its own base URL pointing to the respective API endpoint. Here is an example of how to do this in JavaScript using the Ory Client SDK:
Copy code
javascript import { Configuration, PublicApi, AdminApi } from "@ory/client"      const kratosPublic = new PublicApi(     new Configuration({       basePath: "<https://public.kratos:4433/>",     }),   )      const kratosAdmin = new AdminApi(     new Configuration({       basePath: "<https://admin.kratos:4434/>",     }),   )
In this example,
kratosPublic
is the instance for the public API and
kratosAdmin
is the instance for the admin API. You can switch between them by using the respective instance for the operation you want to perform. Please note that you need to replace
"<https://public.kratos:4433/>"
and
"<https://admin.kratos:4434/>"
with the actual URLs of your public and admin APIs. For more information, you can refer to the [Ory Kratos JavaScript SDK documentation](https://www.ory.sh/docs/hydra/sdk/js). Remember to secure your admin API properly as it can perform sensitive operations. It's recommended to make the admin API inaccessible via the public internet by setting
serve.admin.host
to
127.0.0.1
to ensure Ory Kratos is listening on the loopback interface. This is mentioned in the [Ory Kratos guide on deploying to production](https://www.ory.sh/docs/kratos/guides/deploy-kratos-example#run-ory-kratos-using-systemd).
g
@chilly-king-10285 Do you have the same but in Go?
c
A message from kapa.ai
Sure, here is an example of how to configure your Kratos client in Go to have both the public and admin API available:
Copy code
go package main  import (  "<http://github.com/ory/kratos-client-go/client|github.com/ory/kratos-client-go/client>"  "<http://github.com/ory/kratos-client-go/client/admin|github.com/ory/kratos-client-go/client/admin>"  "<http://github.com/ory/kratos-client-go/client/public|github.com/ory/kratos-client-go/client/public>" )  func main() {  // Create a new Kratos admin client  adminClient := client.NewHTTPClientWithConfig(nil, &client.TransportConfig{   Host:     "admin.kratos:4434",   BasePath: "/",   Schemes:  []string{"https"},  })   // Create a new Kratos public client  publicClient := client.NewHTTPClientWithConfig(nil, &client.TransportConfig{   Host:     "public.kratos:4433",   BasePath: "/",   Schemes:  []string{"https"},  })   // Now you can use adminClient and publicClient to make requests to the admin and public APIs respectively  // For example, to list identities using the admin API:  params := admin.NewListIdentitiesParams()  adminClient.Admin.ListIdentities(params)   // And to get a self-service registration flow with the public API:  params := public.NewGetSelfServiceRegistrationFlowParams().WithID(flowID)  publicClient.Public.GetSelfServiceRegistrationFlow(params) }
In this example,
adminClient
is the instance for the admin API and
publicClient
is the instance for the public API. You can switch between them by using the respective instance for the operation you want to perform. Please note that you need to replace
"admin.kratos:4434"
and
"public.kratos:4433"
with the actual URLs of your admin and public APIs. For more information, you can refer to the [Ory Kratos Go SDK documentation](https://www.ory.sh/docs/hydra/sdk/go). Remember to secure your admin API properly as it can perform sensitive operations. It's recommended to make the admin API inaccessible via the public internet by setting
serve.admin.host
to
127.0.0.1
to ensure Ory Kratos is listening on the loopback interface. This is mentioned in the [Ory Kratos guide on deploying to production](https://www.ory.sh/docs/kratos/guides/deploy-kratos-example#run-ory-kratos-using-systemd).
g
@chilly-king-10285 How do I use the kratos client OperationServers property?
c
A message from kapa.ai
The
OperationServers
property in the Ory Kratos Go SDK is used to specify different servers for different API operations. This can be useful when you have different endpoints for different operations, such as a separate endpoint for admin operations. Here's an example of how you might use it:
Copy code
go package main  import (  "context"  "<http://github.com/ory/kratos-client-go/client|github.com/ory/kratos-client-go/client>"  "<http://github.com/ory/kratos-client-go/client/admin|github.com/ory/kratos-client-go/client/admin>" )  func main() {  configuration := client.NewConfiguration()  configuration.Servers = []client.ServerConfiguration{   {    URL: "<http://127.0.0.1:4434>", // Kratos Admin API   },  }   apiClient := client.NewAPIClient(configuration)   // Use OperationServers to specify a different server for a specific operation  apiClient.Admin.ListIdentities.OperationServers = map[string]string{   "default": "<http://different.server:4434>",  }   // Now when you call ListIdentities, it will use the server specified in OperationServers  _, _, err := apiClient.Admin.ListIdentities(context.Background(), &admin.ListIdentitiesParams{})  if err != nil {   // handle error  } }
In this example, we're setting a different server for the
ListIdentities
operation. When we call
ListIdentities
, it will use the server specified in
OperationServers
instead of the default server specified in the
configuration
. Please note that the
OperationServers
property is not available in all SDKs. If you're using a different SDK, you might need to use a different method to specify different servers for different operations. For more information, you can refer to the [Ory Kratos Go SDK documentation](https://www.ory.sh/docs/kratos/self-hosted/go).
g
@chilly-king-10285 Is there a way I can introduce a header to be checked by my Admin API in self hosted before accepting requests?
c
A message from kapa.ai
Yes, you can introduce a header to be checked by your Admin API before accepting requests. This can be done by configuring Nginx (or any other reverse proxy) to check for the presence and/or value of a specific header before forwarding the request to your Admin API. Here is an example of how you can do this in Nginx:
Copy code
nginx location /admin {     # Check for the presence of the 'X-Admin-API-Key' header     if ($http_x_admin_api_key = "") {         return 403;     }      # Check the value of the 'X-Admin-API-Key' header     if ($http_x_admin_api_key != "your-api-key") {         return 403;     }      proxy_pass <http://admin_api>;     proxy_redirect off;     proxy_set_header Host $host;     proxy_set_header X-Real-IP $remote_addr;     proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for; }
In this example, Nginx checks for the presence of the 'X-Admin-API-Key' header and its value. If the header is not present or the value is not correct, Nginx returns a 403 response, preventing the request from reaching your Admin API. Please replace
"your-api-key"
with your actual API key. This is just an example and the actual implementation may vary depending on your specific requirements and the reverse proxy you are using. For more information, you can refer to the [Ory Hydra guide on deploying to production](https://www.ory.sh/docs/hydra/self-hosted/deploy-hydra-example#install-and-configure-nginx) and the [Ory Kratos guide on deploying to production](https://www.ory.sh/docs/kratos/guides/deploy-kratos-example#install-and-configure-nginx).
g
@chilly-king-10285 Is there a way I can disable an identity without deleting it? Preventing it from signing in?
c
A message from kapa.ai
Yes, you can disable an identity without deleting it in Ory. This will prevent the identity from using self-service flows such as sign-in. You can do this by changing the identity state to
inactive
. Here is an example of how to do this using the Ory SDK in JavaScript:
Copy code
javascript import { Configuration, IdentityApi } from "@ory/client"   import { JsonPatchOpEnum } from "@ory/client/api"      const identity = new IdentityApi(     new Configuration({       basePath: `https://${process.env.ORY_PROJECT_SLUG}.<http://projects.oryapis.com|projects.oryapis.com>`,       accessToken: process.env.ORY_API_KEY,     }),   )      export async function setState(     identityId: string,     state: "active" | "inactive",   ) {     return await identity       .patchIdentity({         id: identityId,         jsonPatch: [           {             op: JsonPatchOpEnum.Replace,             value: state,             path: "/state",           },         ],       })       .then(({ data }) => data)   }
And here is how to do it in Go:
Copy code
go package identity      import (    "context"    "fmt"    "os"       client "<http://github.com/ory/client-go|github.com/ory/client-go>"   )      var authed = context.WithValue(context.Background(), client.ContextAccessToken, os.Getenv("ORY_API_KEY"))      func init() {    cfg := client.NewConfiguration()    cfg.Servers = client.ServerConfigurations{     {URL: fmt.Sprintf("<https://%s.projects.oryapis.com>", os.Getenv("ORY_PROJECT_SLUG"))},    }       ory = client.NewAPIClient(cfg)   }      func setState(identityId string, state string) (err error) {    _, _, err = ory.IdentityApi.     PatchIdentity(authed, identityId).     JsonPatch([]client.JsonPatch{{Op: "replace", Path: "/state", Value: state}}).Execute()    return err   }
In both examples, you need to replace
identityId
with the ID of the identity you want to disable, and
state
with
"inactive"
. For more information, you can refer to the [Ory documentation on changing the identity state](https://www.ory.sh/docs/identities/model/activate-deactivate-user-login-state).