Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

feat: support list users #57

Merged
merged 5 commits into from
Apr 30, 2024
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
8 changes: 4 additions & 4 deletions .github/workflows/main.yaml
Original file line number Diff line number Diff line change
Expand Up @@ -11,7 +11,7 @@ jobs:
runs-on: ubuntu-latest

steps:
- uses: actions/checkout@b4ffde65f46336ab88eb53be808477a3936bae11 # v4.1.1
- uses: actions/checkout@0ad4b8fadaa221de15dcec353f45205ec38ea70b # v4.1.4
with:
fetch-depth: 0

Expand All @@ -35,7 +35,7 @@ jobs:
path: src/OpenFga.Sdk/bin/Release/OpenFga.Sdk.*.nupkg

- name: Upload coverage to Codecov
uses: codecov/codecov-action@c16abc29c95fcf9174b58eb7e1abf4c866893bc8 # v4.1.1
uses: codecov/codecov-action@84508663e988701840491b86de86b666e8a86bed # v4.3.0
continue-on-error: true
with:
token: ${{ secrets.CODECOV_TOKEN }}
Expand All @@ -47,7 +47,7 @@ jobs:
needs: [test]

steps:
- uses: actions/checkout@b4ffde65f46336ab88eb53be808477a3936bae11 # v4.1.1
- uses: actions/checkout@0ad4b8fadaa221de15dcec353f45205ec38ea70b # v4.1.4
with:
fetch-depth: 0

Expand Down Expand Up @@ -81,7 +81,7 @@ jobs:
needs: publish

steps:
- uses: actions/checkout@b4ffde65f46336ab88eb53be808477a3936bae11 # v4.1.1
- uses: actions/checkout@0ad4b8fadaa221de15dcec353f45205ec38ea70b # v4.1.4
with:
fetch-depth: 0

Expand Down
2 changes: 1 addition & 1 deletion .github/workflows/semgrep.yaml
Original file line number Diff line number Diff line change
Expand Up @@ -11,7 +11,7 @@ jobs:
image: returntocorp/semgrep
if: (github.actor != 'dependabot[bot]' && github.actor != 'snyk-bot')
steps:
- uses: actions/checkout@b4ffde65f46336ab88eb53be808477a3936bae11 # v4.1.1
- uses: actions/checkout@0ad4b8fadaa221de15dcec353f45205ec38ea70b # v4.1.4
with:
fetch-depth: 0
- run: semgrep ci --no-suppress-errors
Expand Down
21 changes: 21 additions & 0 deletions .openapi-generator/FILES
Original file line number Diff line number Diff line change
Expand Up @@ -37,18 +37,22 @@ docs/ErrorCode.md
docs/ExpandRequest.md
docs/ExpandRequestTupleKey.md
docs/ExpandResponse.md
docs/FgaObject.md
docs/GetStoreResponse.md
docs/InternalErrorCode.md
docs/InternalErrorMessageResponse.md
docs/Leaf.md
docs/ListObjectsRequest.md
docs/ListObjectsResponse.md
docs/ListStoresResponse.md
docs/ListUsersRequest.md
docs/ListUsersResponse.md
docs/Metadata.md
docs/Node.md
docs/Nodes.md
docs/NotFoundErrorCode.md
docs/NullValue.md
docs/ObjectOrUserset.md
docs/ObjectRelation.md
docs/OpenFgaApi.md
docs/PathUnknownErrorMessageResponse.md
Expand All @@ -73,11 +77,17 @@ docs/TupleOperation.md
docs/TupleToUserset.md
docs/TypeDefinition.md
docs/TypeName.md
docs/TypedWildcard.md
docs/UnprocessableContentErrorCode.md
docs/UnprocessableContentMessageResponse.md
docs/User.md
docs/UserTypeFilter.md
docs/Users.md
docs/Userset.md
docs/UsersetTree.md
docs/UsersetTreeDifference.md
docs/UsersetTreeTupleToUserset.md
docs/UsersetUser.md
docs/Usersets.md
docs/ValidationErrorMessageResponse.md
docs/WriteAssertionsRequest.md
Expand Down Expand Up @@ -116,6 +126,7 @@ src/OpenFga.Sdk/Client/Model/ClientListRelationsOptions.cs
src/OpenFga.Sdk/Client/Model/ClientListRelationsRequest.cs
src/OpenFga.Sdk/Client/Model/ClientListRelationsResponse.cs
src/OpenFga.Sdk/Client/Model/ClientListStoresOptions.cs
src/OpenFga.Sdk/Client/Model/ClientListUsersRequest.cs
src/OpenFga.Sdk/Client/Model/ClientPaginationOptions.cs
src/OpenFga.Sdk/Client/Model/ClientReadAssertionsOptions.cs
src/OpenFga.Sdk/Client/Model/ClientReadAuthorizaionModelOptions.cs
Expand Down Expand Up @@ -173,6 +184,7 @@ src/OpenFga.Sdk/Model/ErrorCode.cs
src/OpenFga.Sdk/Model/ExpandRequest.cs
src/OpenFga.Sdk/Model/ExpandRequestTupleKey.cs
src/OpenFga.Sdk/Model/ExpandResponse.cs
src/OpenFga.Sdk/Model/FgaObject.cs
src/OpenFga.Sdk/Model/GetStoreResponse.cs
src/OpenFga.Sdk/Model/InternalErrorCode.cs
src/OpenFga.Sdk/Model/InternalErrorMessageResponse.cs
Expand All @@ -181,11 +193,14 @@ src/OpenFga.Sdk/Model/Leaf.cs
src/OpenFga.Sdk/Model/ListObjectsRequest.cs
src/OpenFga.Sdk/Model/ListObjectsResponse.cs
src/OpenFga.Sdk/Model/ListStoresResponse.cs
src/OpenFga.Sdk/Model/ListUsersRequest.cs
src/OpenFga.Sdk/Model/ListUsersResponse.cs
src/OpenFga.Sdk/Model/Metadata.cs
src/OpenFga.Sdk/Model/Node.cs
src/OpenFga.Sdk/Model/Nodes.cs
src/OpenFga.Sdk/Model/NotFoundErrorCode.cs
src/OpenFga.Sdk/Model/NullValue.cs
src/OpenFga.Sdk/Model/ObjectOrUserset.cs
src/OpenFga.Sdk/Model/ObjectRelation.cs
src/OpenFga.Sdk/Model/PathUnknownErrorMessageResponse.cs
src/OpenFga.Sdk/Model/ReadAssertionsResponse.cs
Expand All @@ -209,11 +224,17 @@ src/OpenFga.Sdk/Model/TupleOperation.cs
src/OpenFga.Sdk/Model/TupleToUserset.cs
src/OpenFga.Sdk/Model/TypeDefinition.cs
src/OpenFga.Sdk/Model/TypeName.cs
src/OpenFga.Sdk/Model/TypedWildcard.cs
src/OpenFga.Sdk/Model/UnprocessableContentErrorCode.cs
src/OpenFga.Sdk/Model/UnprocessableContentMessageResponse.cs
src/OpenFga.Sdk/Model/User.cs
src/OpenFga.Sdk/Model/UserTypeFilter.cs
src/OpenFga.Sdk/Model/Users.cs
src/OpenFga.Sdk/Model/Userset.cs
src/OpenFga.Sdk/Model/UsersetTree.cs
src/OpenFga.Sdk/Model/UsersetTreeDifference.cs
src/OpenFga.Sdk/Model/UsersetTreeTupleToUserset.cs
src/OpenFga.Sdk/Model/UsersetUser.cs
src/OpenFga.Sdk/Model/Usersets.cs
src/OpenFga.Sdk/Model/ValidationErrorMessageResponse.cs
src/OpenFga.Sdk/Model/WriteAssertionsRequest.cs
Expand Down
10 changes: 9 additions & 1 deletion CHANGELOG.md
Original file line number Diff line number Diff line change
@@ -1,5 +1,13 @@
# Changelog

## v0.3.2

### [0.3.2](https://github.com/openfga/dotnet-sdk/compare/v0.3.1...v0.3.2) (2024-04-30)

- feat: support the [ListUsers](https://github.com/openfga/rfcs/blob/main/20231214-listUsers-api.md) endpoint (#57)
- feat: add retries to client credential requests (#51)
- feat: add support for modular models metadata (#53)

## v0.3.1

### [0.3.1](https://github.com/openfga/dotnet-sdk/compare/v0.3.0...v0.3.1) (2024-02-13)
Expand Down Expand Up @@ -38,7 +46,7 @@ Some of the changes to expect:
var configuration = new ClientConfiguration() {
ApiUrl = Environment.GetEnvironmentVariable("FGA_API_URL"), // required, e.g. https://api.fga.example
StoreId = Environment.GetEnvironmentVariable("FGA_STORE_ID"), // not needed when calling `CreateStore` or `ListStores`
AuthorizationModelId = Environment.GetEnvironmentVariable("FGA_AUTHORIZATION_MODEL_ID"), // Optional, can be overridden per request
AuthorizationModelId = Environment.GetEnvironmentVariable("FGA_MODEL_ID"), // Optional, can be overridden per request
};
var fgaClient = new OpenFgaClient(configuration);
```
Expand Down
63 changes: 59 additions & 4 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -38,6 +38,7 @@ This is an autogenerated SDK for OpenFGA. It provides a wrapper around the [Open
- [Expand](#expand)
- [List Objects](#list-objects)
- [List Relations](#list-relations)
- [List Users](#list-users)
- [Assertions](#assertions)
- [Read Assertions](#read-assertions)
- [Write Assertions](#write-assertions)
Expand Down Expand Up @@ -111,7 +112,7 @@ namespace Example {
var configuration = new ClientConfiguration() {
ApiUrl = Environment.GetEnvironmentVariable("FGA_API_URL") ?? "http://localhost:8080", // required, e.g. https://api.fga.example
StoreId = Environment.GetEnvironmentVariable("FGA_STORE_ID"), // not needed when calling `CreateStore` or `ListStores`
AuthorizationModelId = Environment.GetEnvironmentVariable("FGA_AUTHORIZATION_MODEL_ID"), // Optional, can be overridden per request
AuthorizationModelId = Environment.GetEnvironmentVariable("FGA_MODEL_ID"), // Optional, can be overridden per request
};
var fgaClient = new OpenFgaClient(configuration);
var response = await fgaClient.ReadAuthorizationModels();
Expand All @@ -137,7 +138,7 @@ namespace Example {
var configuration = new ClientConfiguration() {
ApiUrl = Environment.GetEnvironmentVariable("FGA_API_URL") ?? "http://localhost:8080", // required, e.g. https://api.fga.example
StoreId = Environment.GetEnvironmentVariable("FGA_STORE_ID"), // not needed when calling `CreateStore` or `ListStores`
AuthorizationModelId = Environment.GetEnvironmentVariable("FGA_AUTHORIZATION_MODEL_ID"), // Optional, can be overridden per request
AuthorizationModelId = Environment.GetEnvironmentVariable("FGA_MODEL_ID"), // Optional, can be overridden per request
Credentials = new Credentials() {
Method = CredentialsMethod.ApiToken,
Config = new CredentialsConfig() {
Expand Down Expand Up @@ -169,7 +170,7 @@ namespace Example {
var configuration = new ClientConfiguration() {
ApiUrl = Environment.GetEnvironmentVariable("FGA_API_URL") ?? "http://localhost:8080", // required, e.g. https://api.fga.example
StoreId = Environment.GetEnvironmentVariable("FGA_STORE_ID"), // not needed when calling `CreateStore` or `ListStores`
AuthorizationModelId = Environment.GetEnvironmentVariable("FGA_AUTHORIZATION_MODEL_ID"), // Optional, can be overridden per request
AuthorizationModelId = Environment.GetEnvironmentVariable("FGA_MODEL_ID"), // Optional, can be overridden per request
Credentials = new Credentials() {
Method = CredentialsMethod.ClientCredentials,
Config = new CredentialsConfig() {
Expand Down Expand Up @@ -705,6 +706,49 @@ var response = await fgaClient.ListRelations(body);
// response.Relations = ["can_view", "can_edit"]
```

##### List Users

List the users who have a certain relation to a particular type.

[API Documentation](https://openfga.dev/api/service#/Relationship%20Queries/ListUsers)

```csharp
const options = {};

// To override the authorization model id for this request
options.authorization_model_id = "1uHxCSuTP0VKPYSnkq1pbb1jeZw";

// Only a single filter is allowed for the time being
const userFilters = [{type: "user"}];
// user filters can also be of the form
// const userFilters = [{type: "team", relation: "member"}];

const response = await fgaClient.listUsers({
object: {
type: "document",
id: "roadmap"
},
relation: "can_read",
user_filters: userFilters,
context: {
"view_count": 100
},
contextualTuples:
[{
user: "user:81684243-9356-4421-8fbf-a4f8d36aa31b",
relation: "editor",
object: "folder:product"
}, {
user: "folder:product",
relation: "parent",
object: "document:roadmap"
}]
}, options);

// response.users = [{object: {type: "user", id: "81684243-9356-4421-8fbf-a4f8d36aa31b"}}, {userset: { type: "user" }}, ...]
// response.excluded_users = [ {object: {type: "user", id: "4a455e27-d15a-4434-82e0-136f9c2aa4cf"}}, ... ]
```

#### Assertions

##### Read Assertions
Expand Down Expand Up @@ -762,7 +806,7 @@ namespace Example {
var configuration = new ClientConfiguration() {
ApiUrl = Environment.GetEnvironmentVariable("FGA_API_URL") ?? "http://localhost:8080", // required, e.g. https://api.fga.example
StoreId = Environment.GetEnvironmentVariable("FGA_STORE_ID"), // not needed when calling `CreateStore` or `ListStores`
AuthorizationModelId = Environment.GetEnvironmentVariable("FGA_AUTHORIZATION_MODEL_ID"), // Optional, can be overridden per request
AuthorizationModelId = Environment.GetEnvironmentVariable("FGA_MODEL_ID"), // Optional, can be overridden per request
RetryParams = new RetryParams() {
MaxRetry = 3, // retry up to 3 times on API requests
MinWaitInMs = 250 // wait a minimum of 250 milliseconds between requests
Expand All @@ -789,6 +833,7 @@ namespace Example {
| [**GetStore**](docs/OpenFgaApi.md#getstore) | **GET** /stores/{store_id} | Get a store |
| [**ListObjects**](docs/OpenFgaApi.md#listobjects) | **POST** /stores/{store_id}/list-objects | List all objects of the given type that the user has a relation with |
| [**ListStores**](docs/OpenFgaApi.md#liststores) | **GET** /stores | List all stores |
| [**ListUsers**](docs/OpenFgaApi.md#listusers) | **POST** /stores/{store_id}/list-users | List all users of the given type that the object has a relation with |
| [**Read**](docs/OpenFgaApi.md#read) | **POST** /stores/{store_id}/read | Get tuples from the store that matches a query, without following userset rewrite rules |
| [**ReadAssertions**](docs/OpenFgaApi.md#readassertions) | **GET** /stores/{store_id}/assertions/{authorization_model_id} | Read assertions for an authorization model ID |
| [**ReadAuthorizationModel**](docs/OpenFgaApi.md#readauthorizationmodel) | **GET** /stores/{store_id}/authorization-models/{id} | Return a particular version of an authorization model |
Expand Down Expand Up @@ -822,18 +867,22 @@ namespace Example {
- [Model.ExpandRequest](docs/ExpandRequest.md)
- [Model.ExpandRequestTupleKey](docs/ExpandRequestTupleKey.md)
- [Model.ExpandResponse](docs/ExpandResponse.md)
- [Model.FgaObject](docs/FgaObject.md)
- [Model.GetStoreResponse](docs/GetStoreResponse.md)
- [Model.InternalErrorCode](docs/InternalErrorCode.md)
- [Model.InternalErrorMessageResponse](docs/InternalErrorMessageResponse.md)
- [Model.Leaf](docs/Leaf.md)
- [Model.ListObjectsRequest](docs/ListObjectsRequest.md)
- [Model.ListObjectsResponse](docs/ListObjectsResponse.md)
- [Model.ListStoresResponse](docs/ListStoresResponse.md)
- [Model.ListUsersRequest](docs/ListUsersRequest.md)
- [Model.ListUsersResponse](docs/ListUsersResponse.md)
- [Model.Metadata](docs/Metadata.md)
- [Model.Node](docs/Node.md)
- [Model.Nodes](docs/Nodes.md)
- [Model.NotFoundErrorCode](docs/NotFoundErrorCode.md)
- [Model.NullValue](docs/NullValue.md)
- [Model.ObjectOrUserset](docs/ObjectOrUserset.md)
- [Model.ObjectRelation](docs/ObjectRelation.md)
- [Model.PathUnknownErrorMessageResponse](docs/PathUnknownErrorMessageResponse.md)
- [Model.ReadAssertionsResponse](docs/ReadAssertionsResponse.md)
Expand All @@ -857,11 +906,17 @@ namespace Example {
- [Model.TupleToUserset](docs/TupleToUserset.md)
- [Model.TypeDefinition](docs/TypeDefinition.md)
- [Model.TypeName](docs/TypeName.md)
- [Model.TypedWildcard](docs/TypedWildcard.md)
- [Model.UnprocessableContentErrorCode](docs/UnprocessableContentErrorCode.md)
- [Model.UnprocessableContentMessageResponse](docs/UnprocessableContentMessageResponse.md)
- [Model.User](docs/User.md)
- [Model.UserTypeFilter](docs/UserTypeFilter.md)
- [Model.Users](docs/Users.md)
- [Model.Userset](docs/Userset.md)
- [Model.UsersetTree](docs/UsersetTree.md)
- [Model.UsersetTreeDifference](docs/UsersetTreeDifference.md)
- [Model.UsersetTreeTupleToUserset](docs/UsersetTreeTupleToUserset.md)
- [Model.UsersetUser](docs/UsersetUser.md)
- [Model.Usersets](docs/Usersets.md)
- [Model.ValidationErrorMessageResponse](docs/ValidationErrorMessageResponse.md)
- [Model.WriteAssertionsRequest](docs/WriteAssertionsRequest.md)
Expand Down
12 changes: 12 additions & 0 deletions docs/FgaObject.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,12 @@
# OpenFga.Sdk.Model.FgaObject
Object represents an OpenFGA Object. An Object is composed of a type and identifier (e.g. 'document:1') See https://openfga.dev/docs/concepts#what-is-an-object

## Properties

Name | Type | Description | Notes
------------ | ------------- | ------------- | -------------
**Type** | **string** | |
**Id** | **string** | |

[[Back to Model list]](../README.md#models) [[Back to API list]](../README.md#api-endpoints) [[Back to README]](../README.md)

15 changes: 15 additions & 0 deletions docs/ListUsersRequest.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,15 @@
# OpenFga.Sdk.Model.ListUsersRequest

## Properties

Name | Type | Description | Notes
------------ | ------------- | ------------- | -------------
**AuthorizationModelId** | **string** | | [optional]
**Object** | [**FgaObject**](FgaObject.md) | |
**Relation** | **string** | |
**UserFilters** | [**List<UserTypeFilter>**](UserTypeFilter.md) | |
**ContextualTuples** | [**List<TupleKey>**](TupleKey.md) | | [optional]
**Context** | **Object** | Additional request context that will be used to evaluate any ABAC conditions encountered in the query evaluation. | [optional]

[[Back to Model list]](../README.md#models) [[Back to API list]](../README.md#api-endpoints) [[Back to README]](../README.md)

11 changes: 11 additions & 0 deletions docs/ListUsersResponse.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,11 @@
# OpenFga.Sdk.Model.ListUsersResponse

## Properties

Name | Type | Description | Notes
------------ | ------------- | ------------- | -------------
**Users** | [**List<User>**](User.md) | |
**ExcludedUsers** | [**List<ObjectOrUserset>**](ObjectOrUserset.md) | |

[[Back to Model list]](../README.md#models) [[Back to API list]](../README.md#api-endpoints) [[Back to README]](../README.md)

11 changes: 11 additions & 0 deletions docs/ObjectOrUserset.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,11 @@
# OpenFga.Sdk.Model.ObjectOrUserset

## Properties

Name | Type | Description | Notes
------------ | ------------- | ------------- | -------------
**Object** | [**FgaObject**](FgaObject.md) | | [optional]
**Userset** | [**UsersetUser**](UsersetUser.md) | | [optional]

[[Back to Model list]](../README.md#models) [[Back to API list]](../README.md#api-endpoints) [[Back to README]](../README.md)

Loading
Loading