feat: Add Official Microsoft & Gemini Skills (845+ Total)
🚀 Impact Significantly expands the capabilities of **Antigravity Awesome Skills** by integrating official skill collections from **Microsoft** and **Google Gemini**. This update increases the total skill count to **845+**, making the library even more comprehensive for AI coding assistants. ✨ Key Changes 1. New Official Skills - **Microsoft Skills**: Added a massive collection of official skills from [microsoft/skills](https://github.com/microsoft/skills). - Includes Azure, .NET, Python, TypeScript, and Semantic Kernel skills. - Preserves the original directory structure under `skills/official/microsoft/`. - Includes plugin skills from the `.github/plugins` directory. - **Gemini Skills**: Added official Gemini API development skills under `skills/gemini-api-dev/`. 2. New Scripts & Tooling - **`scripts/sync_microsoft_skills.py`**: A robust synchronization script that: - Clones the official Microsoft repository. - Preserves the original directory heirarchy. - Handles symlinks and plugin locations. - Generates attribution metadata. - **`scripts/tests/inspect_microsoft_repo.py`**: Debug tool to inspect the remote repository structure. - **`scripts/tests/test_comprehensive_coverage.py`**: Verification script to ensure 100% of skills are captured during sync. 3. Core Improvements - **`scripts/generate_index.py`**: Enhanced frontmatter parsing to safely handle unquoted values containing `@` symbols and commas (fixing issues with some Microsoft skill descriptions). - **`package.json`**: Added `sync:microsoft` and `sync:all-official` scripts for easy maintenance. 4. Documentation - Updated `README.md` to reflect the new skill counts (845+) and added Microsoft/Gemini to the provider list. - Updated `CATALOG.md` and `skills_index.json` with the new skills. 🧪 Verification - Ran `scripts/tests/test_comprehensive_coverage.py` to verify all Microsoft skills are detected. - Validated `generate_index.py` fixes by successfully indexing the new skills.
This commit is contained in:
356
skills/official/microsoft/dotnet/data/redis/SKILL.md
Normal file
356
skills/official/microsoft/dotnet/data/redis/SKILL.md
Normal file
@@ -0,0 +1,356 @@
|
||||
---
|
||||
name: azure-resource-manager-redis-dotnet
|
||||
description: |
|
||||
Azure Resource Manager SDK for Redis in .NET. Use for MANAGEMENT PLANE operations: creating/managing Azure Cache for Redis instances, firewall rules, access keys, patch schedules, linked servers (geo-replication), and private endpoints via Azure Resource Manager. NOT for data plane operations (get/set keys, pub/sub) - use StackExchange.Redis for that. Triggers: "Redis cache", "create Redis", "manage Redis", "ARM Redis", "RedisResource", "provision Redis", "Azure Cache for Redis".
|
||||
package: Azure.ResourceManager.Redis
|
||||
---
|
||||
|
||||
# Azure.ResourceManager.Redis (.NET)
|
||||
|
||||
Management plane SDK for provisioning and managing Azure Cache for Redis resources via Azure Resource Manager.
|
||||
|
||||
> **⚠️ Management vs Data Plane**
|
||||
> - **This SDK (Azure.ResourceManager.Redis)**: Create caches, configure firewall rules, manage access keys, set up geo-replication
|
||||
> - **Data Plane SDK (StackExchange.Redis)**: Get/set keys, pub/sub, streams, Lua scripts
|
||||
|
||||
## Installation
|
||||
|
||||
```bash
|
||||
dotnet add package Azure.ResourceManager.Redis
|
||||
dotnet add package Azure.Identity
|
||||
```
|
||||
|
||||
**Current Version**: 1.5.1 (Stable)
|
||||
**API Version**: 2024-11-01
|
||||
**Target Frameworks**: .NET 8.0, .NET Standard 2.0
|
||||
|
||||
## Environment Variables
|
||||
|
||||
```bash
|
||||
AZURE_SUBSCRIPTION_ID=<your-subscription-id>
|
||||
# For service principal auth (optional)
|
||||
AZURE_TENANT_ID=<tenant-id>
|
||||
AZURE_CLIENT_ID=<client-id>
|
||||
AZURE_CLIENT_SECRET=<client-secret>
|
||||
```
|
||||
|
||||
## Authentication
|
||||
|
||||
```csharp
|
||||
using Azure.Identity;
|
||||
using Azure.ResourceManager;
|
||||
using Azure.ResourceManager.Redis;
|
||||
|
||||
// Always use DefaultAzureCredential
|
||||
var credential = new DefaultAzureCredential();
|
||||
var armClient = new ArmClient(credential);
|
||||
|
||||
// Get subscription
|
||||
var subscriptionId = Environment.GetEnvironmentVariable("AZURE_SUBSCRIPTION_ID");
|
||||
var subscription = armClient.GetSubscriptionResource(
|
||||
new ResourceIdentifier($"/subscriptions/{subscriptionId}"));
|
||||
```
|
||||
|
||||
## Resource Hierarchy
|
||||
|
||||
```
|
||||
ArmClient
|
||||
└── SubscriptionResource
|
||||
└── ResourceGroupResource
|
||||
└── RedisResource
|
||||
├── RedisFirewallRuleResource
|
||||
├── RedisPatchScheduleResource
|
||||
├── RedisLinkedServerWithPropertyResource
|
||||
├── RedisPrivateEndpointConnectionResource
|
||||
└── RedisCacheAccessPolicyResource
|
||||
```
|
||||
|
||||
## Core Workflows
|
||||
|
||||
### 1. Create Redis Cache
|
||||
|
||||
```csharp
|
||||
using Azure.ResourceManager.Redis;
|
||||
using Azure.ResourceManager.Redis.Models;
|
||||
|
||||
// Get resource group
|
||||
var resourceGroup = await subscription
|
||||
.GetResourceGroupAsync("my-resource-group");
|
||||
|
||||
// Define cache configuration
|
||||
var cacheData = new RedisCreateOrUpdateContent(
|
||||
location: AzureLocation.EastUS,
|
||||
sku: new RedisSku(RedisSkuName.Standard, RedisSkuFamily.BasicOrStandard, 1))
|
||||
{
|
||||
EnableNonSslPort = false,
|
||||
MinimumTlsVersion = RedisTlsVersion.Tls1_2,
|
||||
RedisConfiguration = new RedisCommonConfiguration
|
||||
{
|
||||
MaxMemoryPolicy = "volatile-lru"
|
||||
},
|
||||
Tags =
|
||||
{
|
||||
["environment"] = "production"
|
||||
}
|
||||
};
|
||||
|
||||
// Create cache (long-running operation)
|
||||
var cacheCollection = resourceGroup.Value.GetAllRedis();
|
||||
var operation = await cacheCollection.CreateOrUpdateAsync(
|
||||
WaitUntil.Completed,
|
||||
"my-redis-cache",
|
||||
cacheData);
|
||||
|
||||
RedisResource cache = operation.Value;
|
||||
Console.WriteLine($"Cache created: {cache.Data.HostName}");
|
||||
```
|
||||
|
||||
### 2. Get Redis Cache
|
||||
|
||||
```csharp
|
||||
// Get existing cache
|
||||
var cache = await resourceGroup.Value
|
||||
.GetRedisAsync("my-redis-cache");
|
||||
|
||||
Console.WriteLine($"Host: {cache.Value.Data.HostName}");
|
||||
Console.WriteLine($"Port: {cache.Value.Data.Port}");
|
||||
Console.WriteLine($"SSL Port: {cache.Value.Data.SslPort}");
|
||||
Console.WriteLine($"Provisioning State: {cache.Value.Data.ProvisioningState}");
|
||||
```
|
||||
|
||||
### 3. Update Redis Cache
|
||||
|
||||
```csharp
|
||||
var patchData = new RedisPatch
|
||||
{
|
||||
Sku = new RedisSku(RedisSkuName.Standard, RedisSkuFamily.BasicOrStandard, 2),
|
||||
RedisConfiguration = new RedisCommonConfiguration
|
||||
{
|
||||
MaxMemoryPolicy = "allkeys-lru"
|
||||
}
|
||||
};
|
||||
|
||||
var updateOperation = await cache.Value.UpdateAsync(
|
||||
WaitUntil.Completed,
|
||||
patchData);
|
||||
```
|
||||
|
||||
### 4. Delete Redis Cache
|
||||
|
||||
```csharp
|
||||
await cache.Value.DeleteAsync(WaitUntil.Completed);
|
||||
```
|
||||
|
||||
### 5. Get Access Keys
|
||||
|
||||
```csharp
|
||||
var keys = await cache.Value.GetKeysAsync();
|
||||
Console.WriteLine($"Primary Key: {keys.Value.PrimaryKey}");
|
||||
Console.WriteLine($"Secondary Key: {keys.Value.SecondaryKey}");
|
||||
```
|
||||
|
||||
### 6. Regenerate Access Keys
|
||||
|
||||
```csharp
|
||||
var regenerateContent = new RedisRegenerateKeyContent(RedisRegenerateKeyType.Primary);
|
||||
var newKeys = await cache.Value.RegenerateKeyAsync(regenerateContent);
|
||||
Console.WriteLine($"New Primary Key: {newKeys.Value.PrimaryKey}");
|
||||
```
|
||||
|
||||
### 7. Manage Firewall Rules
|
||||
|
||||
```csharp
|
||||
// Create firewall rule
|
||||
var firewallData = new RedisFirewallRuleData(
|
||||
startIP: System.Net.IPAddress.Parse("10.0.0.1"),
|
||||
endIP: System.Net.IPAddress.Parse("10.0.0.255"));
|
||||
|
||||
var firewallCollection = cache.Value.GetRedisFirewallRules();
|
||||
var firewallOperation = await firewallCollection.CreateOrUpdateAsync(
|
||||
WaitUntil.Completed,
|
||||
"allow-internal-network",
|
||||
firewallData);
|
||||
|
||||
// List all firewall rules
|
||||
await foreach (var rule in firewallCollection.GetAllAsync())
|
||||
{
|
||||
Console.WriteLine($"Rule: {rule.Data.Name} ({rule.Data.StartIP} - {rule.Data.EndIP})");
|
||||
}
|
||||
|
||||
// Delete firewall rule
|
||||
var ruleToDelete = await firewallCollection.GetAsync("allow-internal-network");
|
||||
await ruleToDelete.Value.DeleteAsync(WaitUntil.Completed);
|
||||
```
|
||||
|
||||
### 8. Configure Patch Schedule (Premium SKU)
|
||||
|
||||
```csharp
|
||||
// Patch schedules require Premium SKU
|
||||
var scheduleData = new RedisPatchScheduleData(
|
||||
new[]
|
||||
{
|
||||
new RedisPatchScheduleSetting(RedisDayOfWeek.Saturday, 2) // 2 AM Saturday
|
||||
{
|
||||
MaintenanceWindow = TimeSpan.FromHours(5)
|
||||
},
|
||||
new RedisPatchScheduleSetting(RedisDayOfWeek.Sunday, 2) // 2 AM Sunday
|
||||
{
|
||||
MaintenanceWindow = TimeSpan.FromHours(5)
|
||||
}
|
||||
});
|
||||
|
||||
var scheduleCollection = cache.Value.GetRedisPatchSchedules();
|
||||
await scheduleCollection.CreateOrUpdateAsync(
|
||||
WaitUntil.Completed,
|
||||
RedisPatchScheduleDefaultName.Default,
|
||||
scheduleData);
|
||||
```
|
||||
|
||||
### 9. Import/Export Data (Premium SKU)
|
||||
|
||||
```csharp
|
||||
// Import data from blob storage
|
||||
var importContent = new ImportRdbContent(
|
||||
files: new[] { "https://mystorageaccount.blob.core.windows.net/container/dump.rdb" },
|
||||
format: "RDB");
|
||||
|
||||
await cache.Value.ImportDataAsync(WaitUntil.Completed, importContent);
|
||||
|
||||
// Export data to blob storage
|
||||
var exportContent = new ExportRdbContent(
|
||||
prefix: "backup",
|
||||
container: "https://mystorageaccount.blob.core.windows.net/container?sastoken",
|
||||
format: "RDB");
|
||||
|
||||
await cache.Value.ExportDataAsync(WaitUntil.Completed, exportContent);
|
||||
```
|
||||
|
||||
### 10. Force Reboot
|
||||
|
||||
```csharp
|
||||
var rebootContent = new RedisRebootContent
|
||||
{
|
||||
RebootType = RedisRebootType.AllNodes,
|
||||
ShardId = 0 // For clustered caches
|
||||
};
|
||||
|
||||
await cache.Value.ForceRebootAsync(rebootContent);
|
||||
```
|
||||
|
||||
## SKU Reference
|
||||
|
||||
| SKU | Family | Capacity | Features |
|
||||
|-----|--------|----------|----------|
|
||||
| Basic | C | 0-6 | Single node, no SLA, dev/test only |
|
||||
| Standard | C | 0-6 | Two nodes (primary/replica), SLA |
|
||||
| Premium | P | 1-5 | Clustering, geo-replication, VNet, persistence |
|
||||
|
||||
**Capacity Sizes (Family C - Basic/Standard)**:
|
||||
- C0: 250 MB
|
||||
- C1: 1 GB
|
||||
- C2: 2.5 GB
|
||||
- C3: 6 GB
|
||||
- C4: 13 GB
|
||||
- C5: 26 GB
|
||||
- C6: 53 GB
|
||||
|
||||
**Capacity Sizes (Family P - Premium)**:
|
||||
- P1: 6 GB per shard
|
||||
- P2: 13 GB per shard
|
||||
- P3: 26 GB per shard
|
||||
- P4: 53 GB per shard
|
||||
- P5: 120 GB per shard
|
||||
|
||||
## Key Types Reference
|
||||
|
||||
| Type | Purpose |
|
||||
|------|---------|
|
||||
| `ArmClient` | Entry point for all ARM operations |
|
||||
| `RedisResource` | Represents a Redis cache instance |
|
||||
| `RedisCollection` | Collection for cache CRUD operations |
|
||||
| `RedisFirewallRuleResource` | Firewall rule for IP filtering |
|
||||
| `RedisPatchScheduleResource` | Maintenance window configuration |
|
||||
| `RedisLinkedServerWithPropertyResource` | Geo-replication linked server |
|
||||
| `RedisPrivateEndpointConnectionResource` | Private endpoint connection |
|
||||
| `RedisCacheAccessPolicyResource` | RBAC access policy |
|
||||
| `RedisCreateOrUpdateContent` | Cache creation payload |
|
||||
| `RedisPatch` | Cache update payload |
|
||||
| `RedisSku` | SKU configuration (name, family, capacity) |
|
||||
| `RedisAccessKeys` | Primary and secondary access keys |
|
||||
| `RedisRegenerateKeyContent` | Key regeneration request |
|
||||
|
||||
## Best Practices
|
||||
|
||||
1. **Use `WaitUntil.Completed`** for operations that must finish before proceeding
|
||||
2. **Use `WaitUntil.Started`** when you want to poll manually or run operations in parallel
|
||||
3. **Always use `DefaultAzureCredential`** — never hardcode keys
|
||||
4. **Handle `RequestFailedException`** for ARM API errors
|
||||
5. **Use `CreateOrUpdateAsync`** for idempotent operations
|
||||
6. **Navigate hierarchy** via `Get*` methods (e.g., `cache.GetRedisFirewallRules()`)
|
||||
7. **Use Premium SKU** for production workloads requiring geo-replication, clustering, or persistence
|
||||
8. **Enable TLS 1.2 minimum** — set `MinimumTlsVersion = RedisTlsVersion.Tls1_2`
|
||||
9. **Disable non-SSL port** — set `EnableNonSslPort = false` for security
|
||||
10. **Rotate keys regularly** — use `RegenerateKeyAsync` and update connection strings
|
||||
|
||||
## Error Handling
|
||||
|
||||
```csharp
|
||||
using Azure;
|
||||
|
||||
try
|
||||
{
|
||||
var operation = await cacheCollection.CreateOrUpdateAsync(
|
||||
WaitUntil.Completed, cacheName, cacheData);
|
||||
}
|
||||
catch (RequestFailedException ex) when (ex.Status == 409)
|
||||
{
|
||||
Console.WriteLine("Cache already exists");
|
||||
}
|
||||
catch (RequestFailedException ex) when (ex.Status == 400)
|
||||
{
|
||||
Console.WriteLine($"Invalid configuration: {ex.Message}");
|
||||
}
|
||||
catch (RequestFailedException ex)
|
||||
{
|
||||
Console.WriteLine($"ARM Error: {ex.Status} - {ex.ErrorCode}: {ex.Message}");
|
||||
}
|
||||
```
|
||||
|
||||
## Common Pitfalls
|
||||
|
||||
1. **SKU downgrades not allowed** — You cannot downgrade from Premium to Standard/Basic
|
||||
2. **Clustering requires Premium** — Shard configuration only available on Premium SKU
|
||||
3. **Geo-replication requires Premium** — Linked servers only work with Premium caches
|
||||
4. **VNet injection requires Premium** — Virtual network support is Premium-only
|
||||
5. **Patch schedules require Premium** — Maintenance windows only configurable on Premium
|
||||
6. **Cache name globally unique** — Redis cache names must be unique across all Azure subscriptions
|
||||
7. **Long provisioning times** — Cache creation can take 15-20 minutes; use `WaitUntil.Started` for async patterns
|
||||
|
||||
## Connecting with StackExchange.Redis (Data Plane)
|
||||
|
||||
After creating the cache with this management SDK, use StackExchange.Redis for data operations:
|
||||
|
||||
```csharp
|
||||
using StackExchange.Redis;
|
||||
|
||||
// Get connection info from management SDK
|
||||
var cache = await resourceGroup.Value.GetRedisAsync("my-redis-cache");
|
||||
var keys = await cache.Value.GetKeysAsync();
|
||||
|
||||
// Connect with StackExchange.Redis
|
||||
var connectionString = $"{cache.Value.Data.HostName}:{cache.Value.Data.SslPort},password={keys.Value.PrimaryKey},ssl=True,abortConnect=False";
|
||||
var connection = ConnectionMultiplexer.Connect(connectionString);
|
||||
var db = connection.GetDatabase();
|
||||
|
||||
// Data operations
|
||||
await db.StringSetAsync("key", "value");
|
||||
var value = await db.StringGetAsync("key");
|
||||
```
|
||||
|
||||
## Related SDKs
|
||||
|
||||
| SDK | Purpose | Install |
|
||||
|-----|---------|---------|
|
||||
| `StackExchange.Redis` | Data plane (get/set, pub/sub, streams) | `dotnet add package StackExchange.Redis` |
|
||||
| `Azure.ResourceManager.Redis` | Management plane (this SDK) | `dotnet add package Azure.ResourceManager.Redis` |
|
||||
| `Microsoft.Azure.StackExchangeRedis` | Azure-specific Redis extensions | `dotnet add package Microsoft.Azure.StackExchangeRedis` |
|
||||
Reference in New Issue
Block a user