Framework Git

Framework Git

Open in ChatGPT
Ask ChatGPT about this page
Open in Claude
Ask Claude about this page

Calling Methods

Sometimes you need more than CRUD, like a report, a custom action, or a
calculation. For that, call a whitelisted function directly over HTTP. Any
Python function decorated with @frappe.whitelist() is reachable at:

/api/method/<dotted.path.to.function>

The path is the function's full import path. See
Whitelisted Methods for how to expose your
own.

A simple call

# my_app/api.py
import frappe

@frappe.whitelist()
def greet(name):
    return f"Hello, {name}!"
curl -G https://example.com/api/method/my_app.api.greet \
  -H "Authorization: token <api_key>:<api_secret>" \
  --data-urlencode 'name=Jane'

The return value comes back under message:

{ "message": "Hello, Jane!" }

Passing arguments

Function arguments map to request parameters by name.

  • GET: pass args as query parameters.
  • POST: pass args as a JSON body (or form fields).
# GET with query params
curl -G https://example.com/api/method/frappe.client.get_value \
  -H "Authorization: token <api_key>:<api_secret>" \
  --data-urlencode 'doctype=ToDo' \
  --data-urlencode 'filters={"status":"Open"}' \
  --data-urlencode 'fieldname=name'
# POST with a JSON body
curl -X POST https://example.com/api/method/my_app.api.greet \
  -H "Authorization: token <api_key>:<api_secret>" \
  -H "Content-Type: application/json" \
  -d '{ "name": "Jane" }'

Complex arguments (lists, dicts) are JSON. As a query param, send the JSON string
URL-encoded. In a POST body, send them as native JSON.

GET vs POST and allow_guest

A whitelisted method that does not opt into specific HTTP methods is callable via
both GET and POST. Restrict it with @frappe.whitelist(methods=["POST"]), and
allow unauthenticated access with @frappe.whitelist(allow_guest=True). Read
Whitelisted Methods before exposing anything
publicly.

Running a method on a document

To run a controller method bound to a specific document, POST to the single
resource with run_method:

curl -X POST https://example.com/api/resource/Sales%20Invoice/INV-0001 \
  -H "Authorization: token <api_key>:<api_secret>" \
  -H "Content-Type: application/json" \
  -d '{ "run_method": "submit" }'

The method must be whitelisted on the controller. GET requires read permission;
POST requires write permission.

In v2 this is a dedicated route:

curl -X POST "https://example.com/api/v2/document/Sales%20Invoice/INV-0001/method/submit" \
  -H "Authorization: token <api_key>:<api_secret>"

Uploading files

Use the built-in upload_file method. Send multipart/form-data with the file
plus optional metadata to attach it to a document:

curl -X POST https://example.com/api/method/upload_file \
  -H "Authorization: token <api_key>:<api_secret>" \
  -F "file=@/path/to/photo.png" \
  -F "doctype=ToDo" \
  -F "docname=abc123" \
  -F "is_private=1"

The response contains the created File document, including its file_url:

{
  "message": {
    "name": "xyz789",
    "file_name": "photo.png",
    "file_url": "/private/files/photo.png",
    "is_private": 1,
    "attached_to_doctype": "ToDo",
    "attached_to_name": "abc123"
  }
}

Omit doctype/docname to upload an unattached file. Use is_private=1 for files
that should require authentication to access.

See also

Last updated 2 hours ago
Was this helpful?
Thanks!