Skip to main content
Version: v2.0

Batch multiple requests

Combine several REST requests into a single HTTP call and read back the per-request results.

When to use this pattern

  • You're making several independent requests in one logical operation (for example, creating an incident and updating a user) and want them to travel in a single round-trip
  • You're reducing latency for many small operations
  • If you're fetching many pages of one collection, use Pagination instead; if the requests depend on each other's results, send them sequentially

Required values

ValueDescription
The requestsBuilt with any builder's ToXRequestInformation method, unsent

Example

The example uses a small helper, batchRequests, that wraps RequestInformation objects into a BatchRequestModel:

package main

import (
"context"
"fmt"
"log"

servicenow "github.com/michaeldcanady/servicenow-sdk-go/v2"
"github.com/michaeldcanady/servicenow-sdk-go/v2/credentials"
abstractions "github.com/microsoft/kiota-abstractions-go"
)

// batchRequests A helper function to combine provided request information into a single `BatchRequest`.
func batchRequests(excludeResponseHeaders bool, requests ...*abstractions.RequestInformation) (*batchapi.BatchRequestModel, error) {
body := batchapi.NewBatchRequestModel()
for _, request := range requests {
restRequest, err := batchapi.CreateRestRequestFromRequestInformation(request, excludeResponseHeaders)
if err != nil {
return nil, err
}
if err := body.AddRequest(restRequest); err != nil {
return nil, err
}
}
return body, nil
}

func main() {
// Step 1: Authenticate and initialize the client
cred := credentials.NewBasicProvider("{username}", "{password}")

client, err := servicenow.NewServiceNowServiceClient(
servicenow.WithAuthenticationProvider(cred),
servicenow.WithInstance("{instance}"),
)
if err != nil {
log.Fatalf("failed to initialize client: %v", err)
}
ctx := context.Background()

// Step 2: Describe the requests to combine — ToXRequestInformation
// builds a request without sending it
var requests []*abstractions.RequestInformation

incidents, err := client.Now().Table("incident").ToGetRequestInformation(ctx, nil)
if err != nil {
log.Fatal(err)
}
users, err := client.Now().Table("sys_user").ToGetRequestInformation(ctx, nil)
if err != nil {
log.Fatal(err)
}
requests = append(requests, incidents, users)

// Step 3: Combine them into one batch body
body, err := batchRequests(true, requests...)
if err != nil {
log.Fatal(err)
}

// Step 4: Send the batch in a single HTTP call
response, err := client.Now().Batch().Post(ctx, body, nil)
if err != nil {
log.Fatalf("batch request failed: %v", err)
}

// Step 5: Inspect the per-request results
serviced, err := response.GetServicedRequests()
if err != nil {
log.Fatal(err)
}
unserviced, err := response.GetUnservicedRequests()
if err != nil {
log.Fatal(err)
}

fmt.Printf("%d requests serviced, %d unserviced\n", len(serviced), len(unserviced))
}

Tips

  • ServiceNow executes the sub-requests independently — a batch isn't a transaction. Check GetUnservicedRequests() for the ones that didn't run.
  • Each serviced request carries its own status code and body; a 200 on the batch only means the batch itself was processed.
  • Any API's requests can be mixed in one batch: table, attachment, and the rest.

Next steps

Was this page helpful?