Skip to main content

Documentation Index

Fetch the complete documentation index at: https://mintlify.com/microsoftgraph/msgraph-sdk-dotnet/llms.txt

Use this file to discover all available pages before exploring further.

Overview

The Groups API provides operations to manage group entities in Azure Active Directory and Microsoft 365. Access through graphClient.Groups.

Request Builder

public GroupsRequestBuilder Groups { get; }
Accessed via: graphClient.Groups

Operations

List Groups

Retrieve a list of group objects.
public async Task<GroupCollectionResponse> GetAsync(
    Action<RequestConfiguration<GroupsRequestBuilderGetQueryParameters>> requestConfiguration = default,
    CancellationToken cancellationToken = default
)
Query Parameters:
$select
string[]
Properties to include (e.g., ["id", "displayName", "mail"])
$filter
string
Filter expression (e.g., "mailEnabled eq true")
$orderby
string[]
Sort order (e.g., ["displayName"])
$top
int
Number of items to return
$skip
int
Number of items to skip
Search query (requires ConsistencyLevel header)
$count
bool
Include count of items
$expand
string[]
Related entities to expand (e.g., ["members"])
Response:
value
Group[]
Array of group objects
URL for next page of results
Example:
// Get all groups
var groups = await graphClient.Groups.GetAsync();

foreach (var group in groups.Value)
{
    Console.WriteLine($"{group.DisplayName} - {group.Mail}");
}

// Filter mail-enabled security groups
var mailGroups = await graphClient.Groups.GetAsync(config =>
{
    config.QueryParameters.Filter = "mailEnabled eq true and securityEnabled eq true";
    config.QueryParameters.Select = new[] { "id", "displayName", "mail" };
});

// Search groups
var searchResults = await graphClient.Groups.GetAsync(config =>
{
    config.QueryParameters.Search = "\"displayName:Engineering\"";
    config.Headers.Add("ConsistencyLevel", "eventual");
});

Create Group

Create a new group.
public async Task<Group> PostAsync(
    Group body,
    Action<RequestConfiguration<DefaultQueryParameters>> requestConfiguration = default,
    CancellationToken cancellationToken = default
)
body
Group
required
Group object with required properties
Required Properties:
  • DisplayName - Group display name
  • MailNickname - Email alias
  • MailEnabled - Whether group is mail-enabled
  • SecurityEnabled - Whether group is security-enabled
Example:
// Create Microsoft 365 group
var newGroup = new Group
{
    DisplayName = "Engineering Team",
    MailNickname = "engineering",
    Description = "Engineering department group",
    MailEnabled = true,
    SecurityEnabled = false,
    GroupTypes = new[] { "Unified" },
    Visibility = "Private"
};

var group = await graphClient.Groups.PostAsync(newGroup);

// Create security group
var securityGroup = new Group
{
    DisplayName = "IT Security",
    MailNickname = "itsecurity",
    MailEnabled = false,
    SecurityEnabled = true
};

var group = await graphClient.Groups.PostAsync(securityGroup);

// Create mail-enabled security group
var mailSecGroup = new Group
{
    DisplayName = "Marketing Team",
    MailNickname = "marketing",
    MailEnabled = true,
    SecurityEnabled = true
};

var group = await graphClient.Groups.PostAsync(mailSecGroup);

Get Group by ID

Retrieve a specific group.
var group = await graphClient.Groups["group-id"].GetAsync();

// Select specific properties
var group = await graphClient.Groups["group-id"].GetAsync(config =>
{
    config.QueryParameters.Select = new[] { "id", "displayName", "description" };
});

// Expand members
var group = await graphClient.Groups["group-id"].GetAsync(config =>
{
    config.QueryParameters.Expand = new[] { "members" };
});

Update Group

Update group properties.
var groupToUpdate = new Group
{
    Description = "Updated description",
    Visibility = "Public"
};

await graphClient.Groups["group-id"].PatchAsync(groupToUpdate);

Delete Group

Delete a group.
await graphClient.Groups["group-id"].DeleteAsync();

Member Management

List Members

var members = await graphClient.Groups["group-id"].Members.GetAsync();

foreach (var member in members.Value)
{
    if (member is User user)
    {
        Console.WriteLine($"User: {user.DisplayName}");
    }
    else if (member is Group group)
    {
        Console.WriteLine($"Group: {group.DisplayName}");
    }
}

Add Member

var directoryObject = new ReferenceCreate
{
    OdataId = $"https://graph.microsoft.com/v1.0/users/{userId}"
};

await graphClient.Groups["group-id"].Members.Ref.PostAsync(directoryObject);

Remove Member

await graphClient.Groups["group-id"].Members["user-id"].Ref.DeleteAsync();

Check Membership

var requestBody = new CheckMemberGroupsPostRequestBody
{
    GroupIds = new[] { "group-id-1", "group-id-2" }
};

var memberGroups = await graphClient.Users["user-id"].CheckMemberGroups.PostAsync(requestBody);

Owner Management

List Owners

var owners = await graphClient.Groups["group-id"].Owners.GetAsync();

Add Owner

var directoryObject = new ReferenceCreate
{
    OdataId = $"https://graph.microsoft.com/v1.0/users/{userId}"
};

await graphClient.Groups["group-id"].Owners.Ref.PostAsync(directoryObject);

Remove Owner

await graphClient.Groups["group-id"].Owners["user-id"].Ref.DeleteAsync();

Additional Methods

Delta Query

Get incremental changes.
var deltaResponse = await graphClient.Groups.Delta.GetAsync();

foreach (var group in deltaResponse.Value)
{
    Console.WriteLine($"Changed group: {group.DisplayName}");
}

Get by IDs

var requestBody = new GetByIdsPostRequestBody
{
    Ids = new List<string> { "group-id-1", "group-id-2" },
    Types = new List<string> { "group" }
};

var groups = await graphClient.DirectoryObjects.GetByIds.PostAsync(requestBody);

Count Groups

var count = await graphClient.Groups.Count.GetAsync();

Group-Specific Operations

List Conversations (Microsoft 365 Groups)

var conversations = await graphClient.Groups["group-id"].Conversations.GetAsync();

List Threads

var threads = await graphClient.Groups["group-id"]
    .Conversations["conversation-id"]
    .Threads.GetAsync();

Access Team (for Teams-enabled groups)

var team = await graphClient.Groups["group-id"].Team.GetAsync();

Access Drive

var drive = await graphClient.Groups["group-id"].Drive.GetAsync();

List Sites

var sites = await graphClient.Groups["group-id"].Sites.GetAsync();

Calendar and Events

// Get group calendar
var calendar = await graphClient.Groups["group-id"].Calendar.GetAsync();

// List events
var events = await graphClient.Groups["group-id"].Events.GetAsync();

// Create event
var newEvent = new Event
{
    Subject = "Team Meeting",
    Start = new DateTimeTimeZone { DateTime = "2024-03-15T14:00:00", TimeZone = "UTC" },
    End = new DateTimeTimeZone { DateTime = "2024-03-15T15:00:00", TimeZone = "UTC" }
};

await graphClient.Groups["group-id"].Events.PostAsync(newEvent);

Common Filtering Examples

// Microsoft 365 groups only
config.QueryParameters.Filter = "groupTypes/any(c:c eq 'Unified')";

// Security groups only
config.QueryParameters.Filter = "securityEnabled eq true and mailEnabled eq false";

// Mail-enabled groups
config.QueryParameters.Filter = "mailEnabled eq true";

// Groups created after date
config.QueryParameters.Filter = "createdDateTime ge 2024-01-01T00:00:00Z";

// Dynamic groups
config.QueryParameters.Filter = "groupTypes/any(c:c eq 'DynamicMembership')";

Group Types

Microsoft 365 Group (Unified)

GroupTypes = new[] { "Unified" },
MailEnabled = true,
SecurityEnabled = false

Security Group

MailEnabled = false,
SecurityEnabled = true

Mail-Enabled Security Group

MailEnabled = true,
SecurityEnabled = true

Dynamic Group

GroupTypes = new[] { "DynamicMembership" },
MembershipRule = "(user.department -eq \"Engineering\")",
MembershipRuleProcessingState = "On"

Pagination

var allGroups = new List<Group>();
var response = await graphClient.Groups.GetAsync(config =>
{
    config.QueryParameters.Top = 100;
});

allGroups.AddRange(response.Value);

while (response.OdataNextLink != null)
{
    response = await graphClient.Groups
        .WithUrl(response.OdataNextLink)
        .GetAsync();
    allGroups.AddRange(response.Value);
}

Error Handling

using Microsoft.Graph.Models.ODataErrors;

try
{
    var group = await graphClient.Groups["invalid-id"].GetAsync();
}
catch (ODataError error)
{
    Console.WriteLine($"Error: {error.Error.Code}");
    Console.WriteLine($"Message: {error.Error.Message}");
}

See Also

Group Model

Group resource properties

Users API

User management

Teams API

Teams operations

Directory Objects

Base directory operations