Go SDK [community]
커뮤니티 SDK
이 SDK는 완전히 커뮤니티에서 관리합니다.
Remnawave Go SDK는 RestAPI와의 편리한 상호작용을 위한 라이브러리입니다.
✨ 주요 기능
- ogen v1.19.0으로 생성: 고처리량을 위한 제로 리플렉션 JSON 디코더
- 타입 안전: OpenAPI 3.0 스펙에 대한 컴파일 타임 검증
- 컨트롤러 기반 설계: 깔끔한 API 접근을 위한 정리된 서브 클라이언트
- 단순화된 시그니처: 간단한 작업을 위한 장황한 Params 구조체 없음
- 컨텍스트 지원: 일급
context.Context지원 - OpenTelemetry: 내장 추적 계측
- 요청 옵션:
...RequestOption을 통한 요청별 커스터마이징 - 에디터: 요청/응답 미들웨어 지원
설치
go get github.com/Jolymmiles/remnawave-api-go/v2@latest
경고
항상 Remnawave 백엔드 버전에 맞는 올바른 버전의 SDK를 선택하고 고정하세요.
| SDK 버전 | Remnawave 패널 버전 |
|---|---|
| v2.6.1 | 2.6.1 |
| v2.5.3 | 2.5.3 |
| v2.3.0-6 | 2.3.0 |
| v2.2.6-3 | 2.2.6 |
사용법
기본 예제
package main
import (
"context"
"fmt"
"log"
remapi "github.com/Jolymmiles/remnawave-api-go/v2/api"
)
func main() {
ctx := context.Background()
// Create base client
baseClient, err := remapi.NewClient(
"https://your-panel.example.com",
remapi.StaticToken{Token: "YOUR_API_TOKEN"},
)
if err != nil {
log.Fatal(err)
}
// Wrap with organized sub-clients
client := remapi.NewClientExt(baseClient)
// Get user by UUID - simplified signature
resp, err := client.Users().GetUserByUuid(ctx, "user-uuid-here")
if err != nil {
log.Fatal(err)
}
switch r := resp.(type) {
case *remapi.UserResponse:
fmt.Printf("User: %s\n", r.Response.Username)
case *remapi.NotFoundError:
fmt.Println("User not found")
case *remapi.BadRequestError:
fmt.Printf("Validation error: %v\n", r.Errors)
}
}
사용자 생성 및 관리
package main
import (
"context"
"fmt"
"log"
remapi "github.com/Jolymmiles/remnawave-api-go/v2/api"
)
func main() {
ctx := context.Background()
baseClient, _ := remapi.NewClient(
"https://your-panel.example.com",
remapi.StaticToken{Token: "YOUR_API_TOKEN"},
)
client := remapi.NewClientExt(baseClient)
// Create user
createResp, err := client.Users().CreateUser(ctx, &remapi.CreateUserRequest{
Username: "john_doe",
})
if err != nil {
log.Fatal(err)
}
user := createResp.(*remapi.UserResponse).Response
fmt.Printf("Created user: %s (UUID: %s)\n", user.Username, user.UUID)
// Disable user
_, err = client.Users().DisableUser(ctx, user.UUID.String())
if err != nil {
log.Fatal(err)
}
fmt.Println("User disabled")
// Enable user
_, err = client.Users().EnableUser(ctx, user.UUID.String())
if err != nil {
log.Fatal(err)
}
fmt.Println("User enabled")
// Delete user
_, err = client.Users().DeleteUser(ctx, user.UUID.String())
if err != nil {
log.Fatal(err)
}
fmt.Println("User deleted")
}
노드 관리
package main
import (
"context"
"fmt"
"log"
remapi "github.com/Jolymmiles/remnawave-api-go/v2/api"
)
func main() {
ctx := context.Background()
baseClient, _ := remapi.NewClient(
"https://your-panel.example.com",
remapi.StaticToken{Token: "YOUR_API_TOKEN"},
)
client := remapi.NewClientExt(baseClient)
// Get all nodes
nodesResp, err := client.Nodes().GetAllNodes(ctx)
if err != nil {
log.Fatal(err)
}
nodes := nodesResp.(*remapi.NodesResponse).Response
fmt.Printf("Total nodes: %d\n", len(nodes))
for _, node := range nodes {
fmt.Printf(" - %s (%s): connected=%v\n",
node.Name, node.Address, node.IsConnected)
}
// Get single node
if len(nodes) > 0 {
nodeResp, _ := client.Nodes().GetOneNode(ctx, nodes[0].UUID.String())
node := nodeResp.(*remapi.NodeResponse).Response
fmt.Printf("\nNode details: %s\n", node.Name)
}
}
페이지네이션
package main
import (
"context"
"fmt"
"log"
remapi "github.com/Jolymmiles/remnawave-api-go/v2/api"
)
func main() {
ctx := context.Background()
baseClient, _ := remapi.NewClient(
"https://your-panel.example.com",
remapi.StaticToken{Token: "YOUR_API_TOKEN"},
)
client := remapi.NewClientExt(baseClient)
// Use PaginationHelper for iterating through pages
pager := remapi.NewPaginationHelper(50) // 50 items per page
for pager.HasMore {
resp, err := client.Users().GetAllUsers(ctx,
pager.Limit, // size
pager.Offset, // start
)
if err != nil {
log.Fatal(err)
}
users := resp.(*remapi.GetAllUsersResponse)
for _, user := range users.Response.Users {
fmt.Printf("User: %s (UUID: %s)\n", user.Username, user.UUID)
}
// Advance to next page
pager.SetTotal(int(users.Response.Total))
pager.NextPage()
}
fmt.Printf("Total users: %d\n", *pager.Total)
}
오류 처리
package main
import (
"context"
"fmt"
"log"
remapi "github.com/Jolymmiles/remnawave-api-go/v2/api"
)
func main() {
ctx := context.Background()
baseClient, _ := remapi.NewClient(
"https://your-panel.example.com",
remapi.StaticToken{Token: "YOUR_API_TOKEN"},
)
client := remapi.NewClientExt(baseClient)
resp, err := client.Users().GetUserByUuid(ctx, "invalid-uuid")
if err != nil {
log.Fatal("Network error:", err)
}
// Available error types depend on the endpoint — check the generated
// Res interface (e.g. UsersGetUserByUuidRes) for the full list.
switch e := resp.(type) {
case *remapi.UserResponse:
fmt.Printf("User found: %s\n", e.Response.Username)
case *remapi.BadRequestError:
fmt.Println("Validation errors:")
for _, ve := range e.Errors {
fmt.Printf(" - %s: %s (path: %v)\n",
ve.Code, ve.Message, ve.Path)
}
case *remapi.NotFoundError:
fmt.Println("Resource not found")
case *remapi.InternalServerError:
fmt.Printf("Server error: %s\n", e.Message.Value)
}
}
사용 가능한 컨트롤러
| 컨트롤러 | 설명 |
|---|---|
client.ApiTokens() | API 토큰 관리 |
client.Auth() | 인증 |
client.BandwidthStatsNodes() | 노드 대역폭 통계 |
client.BandwidthStatsUsers() | 사용자 대역폭 통계 |
client.ConfigProfile() | 설정 프로파일 |
client.ExternalSquad() | 외부 스쿼드 |
client.Hosts() | 호스트 관리 |
client.HostsBulkActions() | 호스트 일괄 작업 |
client.HwidUserDevices() | HWID 장치 |
client.InfraBilling() | 인프라 청구 |
client.InternalSquad() | 내부 스쿼드 |
client.Keygen() | 키 생성 |
client.Nodes() | 노드 관리 |
client.NodesUsageHistory() | 노드 사용 기록 |
client.Passkey() | 패스키 인증 |
client.RemnawaveSettings() | 패널 설정 |
client.Snippets() | 코드 스니펫 |
client.Subscription() | 구독 관리 |
client.SubscriptionPageConfig() | 구독 페이지 설정 |
client.SubscriptionSettings() | 구독 설정 |
client.SubscriptionTemplate() | 구독 템플릿 |
client.Subscriptions() | 다중 구독 |
client.System() | 시스템 정보 |
client.UserSubscriptionRequestHistory() | 요청 기록 |
client.Users() | 사용자 관리 |
client.UsersBulkActions() | 사용자 일괄 작업 |
오류 타입
| 타입 | HTTP 상태 | 설명 |
|---|---|---|
BadRequestError | 400 | 세부 정보가 있는 유효성 검사 오류 |
UnauthorizedError | 401 | 인증 필요 |
ForbiddenError | 403 | 접근 거부 |
NotFoundError | 404 | 리소스를 찾을 수 없음 |
InternalServerError | 500 | 서버 오류 |
🛠️ 프로젝트 링크
- GitHub 저장소: remnawave-api-go on GitHub
- 작성자: Jolymmiles