# HTTP

> lsl.dev (unofficial LSL docs). Full API: https://lsl.dev/api.json · Index for LLMs: https://lsl.dev/llms.txt

> Calling web services with llHTTPRequest, and serving HTTP from an object with its own URL.

Scripts reach the outside world over HTTP. An object can call any web server, and can also act as a small web server itself with a temporary URL. Part of the [Communications](/features/communications/) feature.

## Concepts

- [`llHTTPRequest`](/functions/llHTTPRequest/) sends a request and returns a key; the answer arrives in [`http_response`](/events/http_response/) with the status, metadata and body
  - [Parameters](/constants/groups/HTTPRequestParam/) set the [method](/constants/HTTP_METHOD/), [content type](/constants/HTTP_MIMETYPE/), [custom headers](/constants/HTTP_CUSTOM_HEADER/) and [certificate checks](/constants/HTTP_VERIFY_CERT/)
  - The response body is cut to 2048 bytes by default; [`HTTP_BODY_MAXLENGTH`](/constants/HTTP_BODY_MAXLENGTH/) raises it to 16384 in Mono
  - Requests are throttled per object; a throttled request returns [`NULL_KEY`](/constants/NULL_KEY/)
  - [Escape](/functions/llEscapeURL/) values put into a URL
- An object can serve HTTP
  - [Request a URL](/functions/llRequestURL/) (or a [secure one](/functions/llRequestSecureURL/)); the URL arrives in [`http_request`](/events/http_request/) with the method [`URL_REQUEST_GRANTED`](/constants/URL_REQUEST_GRANTED/)
  - Each incoming request also arrives in `http_request`; [read its headers](/functions/llGetHTTPHeader/) and answer with [`llHTTPResponse`](/functions/llHTTPResponse/) within 25 seconds
  - [`llSetContentType`](/functions/llSetContentType/) sets the type of the response, such as [`CONTENT_TYPE_JSON`](/constants/CONTENT_TYPE_JSON/)
  - URLs are a limited resource: [count the free ones](/functions/llGetFreeURLs/) and [release](/functions/llReleaseURL/) those no longer needed
  - URLs persist across state changes, but are lost when the object changes region or the region restarts; request a new one on [`CHANGED_REGION`](/constants/CHANGED_REGION/), [`CHANGED_REGION_START`](/constants/CHANGED_REGION_START/) and [`on_rez`](/events/on_rez/)
- Objects can call each other's URLs, which is the usual way to talk across regions
- Send structured data as [JSON](/features/data-transmission/json/)

## Functions and events

- `key` [`llHTTPRequest`](/functions/llHTTPRequest/) `(string url, list parameters, string body)`
- `event` [`http_response`](/events/http_response/) `(key request_id, integer status, list metadata, string body)`
- `key` [`llRequestURL`](/functions/llRequestURL/) `()`
- `event` [`http_request`](/events/http_request/) `(key request_id, string method, string body)`
- `void` [`llHTTPResponse`](/functions/llHTTPResponse/) `(key request_id, integer status, string body)`

## Scripting Details

### Requests

- `key` [`llHTTPRequest`](/functions/llHTTPRequest/) `(string url, list parameters, string body)`: Sends an HTTP request to the specified url containing body and configured via parameters. Raises an http_response event and returns a key query handle identifying the request.
- `event` [`http_response`](/events/http_response/) `(key request_id, integer status, list metadata, string body)`: Triggered when an HTTP response body is received for a pending request_id, or if the request fails or times out.
- `string` [`llEscapeURL`](/functions/llEscapeURL/) `(string url)`: Returns a string representing the escaped/encoded version of url, replacing spaces with '%20' and non-alphanumeric characters with their '%xx' hexadecimal UTF-8 equivalent.
- `string` [`llUnescapeURL`](/functions/llUnescapeURL/) `(string url)`: Returns a string representing the unescaped/decoded version of url, replacing '%20' with spaces and decoding raw UTF-8 characters.

### Serving

- `key` [`llRequestURL`](/functions/llRequestURL/) `()`: Asynchronously requests one HTTP URL for use by this script, triggering an http_request event. Returns a key query handle.
- `key` [`llRequestSecureURL`](/functions/llRequestSecureURL/) `()`: Asynchronously requests one secure HTTPS (SSL, port 12043) URL for use by this object, triggering an http_request event. Returns a key query handle.
- `void` [`llReleaseURL`](/functions/llReleaseURL/) `(string url)`: Releases the specified url (previously obtained via llRequestURL), rendering it no longer usable.
- `event` [`http_request`](/events/http_request/) `(key request_id, string method, string body)`: Triggered when the script's registered URL receives an incoming HTTP request identified by request_id.
- `void` [`llHTTPResponse`](/functions/llHTTPResponse/) `(key request_id, integer status, string body)`: Responds to the incoming HTTP request identified by request_id with the HTTP status code status and the payload body.
- `string` [`llGetHTTPHeader`](/functions/llGetHTTPHeader/) `(key request_id, string header)`: Returns a string representing the value of the specified header associated with the HTTP request_id.
- `void` [`llSetContentType`](/functions/llSetContentType/) `(key request_id, integer content_type)`: Sets the 'Content-Type' header of subsequent HTTP server responses (via llHTTPResponse) for request_id using the specified content_type (a CONTENT_TYPE_* constant).
- `integer` [`llGetFreeURLs`](/functions/llGetFreeURLs/) `()`: Returns an integer representing the number of available HTTP URLs (remaining for the owner if the object is attached, or for the region if unattached).

## Example

An object that answers web requests with its region name.

```lsl
default
{
    state_entry()
    {
        llRequestURL();
    }

    on_rez(integer start_param)
    {
        llResetScript();
    }

    changed(integer change)
    {
        if (change & (CHANGED_REGION | CHANGED_REGION_START)) llResetScript();
    }

    http_request(key id, string method, string body)
    {
        if (method == URL_REQUEST_GRANTED)
            llOwnerSay("URL: " + body);
        else if (method == "GET")
            llHTTPResponse(id, 200, llGetRegionName());
        else
            llHTTPResponse(id, 405, "Method not allowed");
    }
}
```

## Constant groups

Constant groups: [HTTPRequestParam](/constants/groups/HTTPRequestParam/) (10), [HTTPContentType](/constants/groups/HTTPContentType/) (9), [HTTPResponseError](/constants/groups/HTTPResponseError/) (1)

## Related

See also: [Communications](/features/communications/), [Web](/categories/web/), [LSL HTTP (Second Life Wiki)](https://wiki.secondlife.com/wiki/Category:LSL_HTTP), [HTTP Server URL Registration (Second Life Wiki)](https://wiki.secondlife.com/wiki/HTTP_Server_URL_Registration), [Data Transmission](/features/data-transmission/)
   (planned: Guide: an object as a web server)

## Related features

- [Communications](/features/communications/)
- [Data Transmission](/features/data-transmission/)

## Categories

- [Web](/categories/web/)
- [Script Communication](/categories/script_communication/)

---

From lsl.dev: https://lsl.dev/features/communications/http/
