Skip to content

Commit 754bdee

Browse files
committed
example added for azure blob storage, accessors re-generated / openapi operations updated
1 parent 2c82308 commit 754bdee

File tree

5 files changed

+1346
-220
lines changed

5 files changed

+1346
-220
lines changed

example/auditlogstream/main.go

Lines changed: 180 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,180 @@
1+
// Copyright 2026 The go-github AUTHORS. All rights reserved.
2+
//
3+
// Use of this source code is governed by a BSD-style
4+
// license that can be found in the LICENSE file.
5+
6+
// The auditlogstream command demonstrates managing enterprise audit log
7+
// streams for Azure Blob Storage using the go-github library.
8+
//
9+
// Usage — create (github.com):
10+
//
11+
// export GITHUB_AUTH_TOKEN=<your token>
12+
// go run main.go create \
13+
// -enterprise=my-enterprise \
14+
// -container=my-container \
15+
// -sas-url=<plain-text-sas-url>
16+
//
17+
// Usage — create (GitHub Enterprise Server):
18+
//
19+
// export GITHUB_AUTH_TOKEN=<your token>
20+
// go run main.go create \
21+
// -base-url=https://github.example.com/api/v3/ \
22+
// -enterprise=my-enterprise \
23+
// -container=my-container \
24+
// -sas-url=<plain-text-sas-url>
25+
//
26+
// Usage — delete:
27+
//
28+
// export GITHUB_AUTH_TOKEN=<your token>
29+
// go run main.go delete \
30+
// -base-url=https://github.example.com/api/v3/ \
31+
// -enterprise=my-enterprise \
32+
// -stream-id=42
33+
package main
34+
35+
import (
36+
"context"
37+
"crypto/rand"
38+
"encoding/base64"
39+
"flag"
40+
"fmt"
41+
"log"
42+
"os"
43+
44+
"github.com/google/go-github/v83/github"
45+
"golang.org/x/crypto/nacl/box"
46+
)
47+
48+
// encryptSecret encrypts a plain-text secret using libsodium's sealed box
49+
// (crypto_box_seal), which is what GitHub's API expects for encrypted credentials.
50+
func encryptSecret(publicKeyB64, secret string) (string, error) {
51+
publicKeyBytes, err := base64.StdEncoding.DecodeString(publicKeyB64)
52+
if err != nil {
53+
return "", fmt.Errorf("decoding public key: %w", err)
54+
}
55+
if len(publicKeyBytes) != 32 {
56+
return "", fmt.Errorf("public key must be 32 bytes, got %d", len(publicKeyBytes))
57+
}
58+
var publicKey [32]byte
59+
copy(publicKey[:], publicKeyBytes)
60+
61+
encrypted, err := box.SealAnonymous(nil, []byte(secret), &publicKey, rand.Reader)
62+
if err != nil {
63+
return "", fmt.Errorf("encrypting secret: %w", err)
64+
}
65+
66+
return base64.StdEncoding.EncodeToString(encrypted), nil
67+
}
68+
69+
func main() {
70+
if len(os.Args) < 2 {
71+
fmt.Fprintf(os.Stderr, "Usage: %s <create|delete> [flags]\n", os.Args[0])
72+
os.Exit(1)
73+
}
74+
75+
switch os.Args[1] {
76+
case "create":
77+
runCreate(os.Args[2:])
78+
case "delete":
79+
runDelete(os.Args[2:])
80+
default:
81+
fmt.Fprintf(os.Stderr, "Unknown command %q. Must be one of: create, delete\n", os.Args[1])
82+
os.Exit(1)
83+
}
84+
}
85+
86+
func runCreate(args []string) {
87+
fs := flag.NewFlagSet("create", flag.ExitOnError)
88+
baseURL := fs.String("base-url", "https://api.github.com/", "GitHub API base URL. For GitHub Enterprise Server use https://HOSTNAME/api/v3/.")
89+
enterprise := fs.String("enterprise", "", "Name of the GitHub enterprise slug (required).")
90+
container := fs.String("container", "", "Azure Blob Storage container name (required).")
91+
sasURL := fs.String("sas-url", "", "Plain-text Azure SAS URL to encrypt and submit (required).")
92+
enabled := fs.Bool("enabled", true, "Whether the stream should be enabled immediately.")
93+
fs.Parse(args)
94+
95+
token := requireEnv("GITHUB_AUTH_TOKEN")
96+
requireFlag("enterprise", *enterprise)
97+
requireFlag("container", *container)
98+
requireFlag("sas-url", *sasURL)
99+
100+
ctx := context.Background()
101+
client := newClient(token, *baseURL)
102+
103+
// Step 1: Fetch the enterprise's public streaming key.
104+
streamKey, _, err := client.Enterprise.GetAuditLogStreamKey(ctx, *enterprise)
105+
if err != nil {
106+
log.Fatalf("Error fetching audit log stream key: %v", err)
107+
}
108+
fmt.Printf("Retrieved stream key ID: %s\n", streamKey.GetKeyID())
109+
110+
// Step 2: Encrypt the SAS URL using the public key (sealed box / crypto_box_seal).
111+
encryptedSASURL, err := encryptSecret(streamKey.GetPublicKey(), *sasURL)
112+
if err != nil {
113+
log.Fatalf("Error encrypting SAS URL: %v", err)
114+
}
115+
fmt.Println("SAS URL encrypted successfully.")
116+
117+
// Step 3: Create the audit log stream.
118+
config := github.NewAzureBlobStreamConfig(*enabled, &github.AzureBlobConfig{
119+
KeyID: streamKey.KeyID,
120+
Container: github.Ptr(*container),
121+
EncryptedSASURL: github.Ptr(encryptedSASURL),
122+
})
123+
124+
stream, _, err := client.Enterprise.CreateAuditLogStream(ctx, *enterprise, config)
125+
if err != nil {
126+
log.Fatalf("Error creating audit log stream: %v", err)
127+
}
128+
129+
fmt.Printf("Successfully created audit log stream:\n")
130+
fmt.Printf(" ID: %d\n", stream.GetID())
131+
fmt.Printf(" Type: %s\n", stream.GetStreamType())
132+
fmt.Printf(" Enabled: %v\n", stream.GetEnabled())
133+
fmt.Printf(" Created at: %v\n", stream.GetCreatedAt())
134+
}
135+
136+
func runDelete(args []string) {
137+
fs := flag.NewFlagSet("delete", flag.ExitOnError)
138+
baseURL := fs.String("base-url", "https://api.github.com/", "GitHub API base URL. For GitHub Enterprise Server use https://HOSTNAME/api/v3/.")
139+
enterprise := fs.String("enterprise", "", "Name of the GitHub enterprise slug (required).")
140+
streamID := fs.Int64("stream-id", 0, "ID of the audit log stream to delete (required).")
141+
fs.Parse(args)
142+
143+
token := requireEnv("GITHUB_AUTH_TOKEN")
144+
requireFlag("enterprise", *enterprise)
145+
if *streamID == 0 {
146+
log.Fatal("flag -stream-id is required")
147+
}
148+
149+
ctx := context.Background()
150+
client := newClient(token, *baseURL)
151+
152+
_, err := client.Enterprise.DeleteAuditLogStream(ctx, *enterprise, *streamID)
153+
if err != nil {
154+
log.Fatalf("Error deleting audit log stream: %v", err)
155+
}
156+
157+
fmt.Printf("Successfully deleted audit log stream %d.\n", *streamID)
158+
}
159+
160+
func newClient(token, baseURL string) *github.Client {
161+
client, err := github.NewClient(nil).WithAuthToken(token).WithEnterpriseURLs(baseURL, baseURL)
162+
if err != nil {
163+
log.Fatalf("Error creating GitHub client: %v", err)
164+
}
165+
return client
166+
}
167+
168+
func requireEnv(name string) string {
169+
val := os.Getenv(name)
170+
if val == "" {
171+
log.Fatalf("environment variable %s is not set", name)
172+
}
173+
return val
174+
}
175+
176+
func requireFlag(name, val string) {
177+
if val == "" {
178+
log.Fatalf("flag -%s is required", name)
179+
}
180+
}

0 commit comments

Comments
 (0)