Deploy your configured flows to make them publicly accessible and executable via the Graphor REST API. Deployment creates a new revision and makes your flow available at a public URL. 
Overview  
The Deploy Flow endpoint creates a new revision of your flow and deploys it, making it accessible for execution via the public API. Once deployed, your flow will be available at https://{flow_name}.flows.graphorlm.com. 
Response Node Required : Your flow must have a configured Response Node  for deployment to work properly. The deployment process validates that all required components, including the Response Node, are properly configured.
 
Method : POST 
URL : https://{flow_name}.flows.graphorlm.com/deploy 
Authentication : Required (API Token) 
 
Authentication  
All requests must include a valid API token in the Authorization header: 
Authorization :  Bearer YOUR_API_TOKEN  
 
Header Value Required AuthorizationBearer YOUR_API_TOKENYes Content-Typeapplication/jsonYes 
 
Request Body  
The request body should be a JSON object with the following optional fields: 
Field Type Required Description tool_descriptionstring No Custom description for the deployed flow that will be used in tool definitions 
 
Example Request  
{  
  "tool_description" :  "Advanced RAG pipeline for technical documentation with semantic search and context-aware responses"  
}  
 
Minimal Request  
For a basic deployment without custom tool description: 
Success Response (200 OK)  
{  
  "success" :  true ,  
  "message" :  "Flow 'my-rag-pipeline' deployed successfully" ,  
  "revision_id" :  "550e8400-e29b-41d4-a716-446655440000" ,  
  "status" :  "Deployed"  
}  
 
Response Fields  
Field Type Description successboolean Whether the deployment was successful messagestring Human-readable message about the deployment revision_idstring Unique identifier for the created revision statusstring Current status of the flow (should be “Deployed”) 
 
Code Examples  
JavaScript/Node.js  
async  function  deployFlow ( flowName ,  toolDescription  =  null ) {  
  const  url  =  `https:// ${ flowName } .flows.graphorlm.com/deploy` ;  
    
  const  payload  =  {};  
  if  ( toolDescription ) {  
    payload . tool_description  =  toolDescription ;  
  }  
 
  const  response  =  await  fetch ( url , {  
    method:  'POST' ,  
    headers:  {  
      'Authorization' :  'Bearer YOUR_API_TOKEN' ,  
      'Content-Type' :  'application/json' ,  
    },  
    body:  JSON . stringify ( payload )  
  });  
 
  if  ( ! response . ok ) {  
    const  errorData  =  await  response . json ();  
    throw  new  Error ( `Deployment failed:  ${ errorData . detail } ` );  
  }  
 
  return  await  response . json ();  
}  
 
// Usage  
deployFlow ( 'my-rag-pipeline' ,  'Advanced document Q&A system' )  
  . then ( result  =>  {  
    console . log ( '✅ Deployment successful!' );  
    console . log ( 'Revision ID:' ,  result . revision_id );  
    console . log ( 'Status:' ,  result . status );  
    console . log ( 'Message:' ,  result . message );  
  })  
  . catch ( error  =>  {  
    console . error ( '❌ Deployment failed:' ,  error . message );  
  });  
 
// Simple deployment without custom description  
deployFlow ( 'my-rag-pipeline' )  
  . then ( result  =>  console . log ( 'Deployed:' ,  result ))  
  . catch ( error  =>  console . error ( 'Error:' ,  error ));  
 
Python  
import  requests  
import  json  
 
def  deploy_flow ( flow_name ,  api_token ,  tool_description = None ):  
    url  =  f "https:// { flow_name } .flows.graphorlm.com/deploy"  
      
    headers  =  {  
        "Authorization" :  f "Bearer  { api_token } " ,  
        "Content-Type" :  "application/json"  
    }  
      
    payload  =  {}  
    if  tool_description:  
        payload[ "tool_description" ]  =  tool_description  
      
    response  =  requests.post(url,  headers = headers,  json = payload)  
    response.raise_for_status()  
      
    return  response.json()  
 
# Usage  
try :  
    result  =  deploy_flow(  
        flow_name = "my-rag-pipeline" ,  
        api_token = "YOUR_API_TOKEN" ,  
        tool_description = "Technical documentation assistant with advanced search capabilities"  
    )  
      
    print ( "✅ Deployment successful!" )  
    print ( f "Revision ID:  { result[ 'revision_id' ] } " )  
    print ( f "Status:  { result[ 'status' ] } " )  
    print ( f "Message:  { result[ 'message' ] } " )  
      
    # Flow is now available at:  
    flow_url  =  f "https:// { result.get( 'flow_name' ,  'my-rag-pipeline' ) } .flows.graphorlm.com"  
    print ( f "🚀 Flow available at:  { flow_url } " )  
      
except  requests.exceptions.HTTPError  as  e:  
    if  e.response.status_code  ==  404 :  
        print ( "❌ Flow not found. Make sure the flow exists and is properly configured." )  
    elif  e.response.status_code  ==  400 :  
        print ( "❌ Invalid flow configuration. Check your flow setup." )  
    else :  
        print ( f "❌ Deployment failed:  { e } " )  
        try :  
            error_detail  =  e.response.json().get( 'detail' ,  'Unknown error' )  
            print ( f "Error details:  { error_detail } " )  
        except :  
            print ( f "HTTP  { e.response.status_code } :  { e.response.text } " )  
 
except  Exception  as  e:  
    print ( f "❌ Unexpected error:  { e } " )  
 
cURL  
# Deploy with custom tool description  
curl  -X  POST  https://my-rag-pipeline.flows.graphorlm.com/deploy  \  
  -H  "Authorization: Bearer YOUR_API_TOKEN"  \  
  -H  "Content-Type: application/json"  \  
  -d  '{  
    "tool_description": "Advanced RAG pipeline for technical documentation"  
  }'  
 
# Simple deployment without custom description  
curl  -X  POST  https://my-rag-pipeline.flows.graphorlm.com/deploy  \  
  -H  "Authorization: Bearer YOUR_API_TOKEN"  \  
  -H  "Content-Type: application/json"  \  
  -d  '{}'  
 
PHP  
<? php  
function  deployFlow ( $flowName ,  $apiToken ,  $toolDescription  =  null ) {  
    $url  =  "https://{ $flowName }.flows.graphorlm.com/deploy" ;  
      
    $payload  =  [];  
    if  ( $toolDescription ) {  
        $payload [ 'tool_description' ]  =  $toolDescription ;  
    }  
      
    $options  =  [  
        'http'  =>  [  
            'header'  =>  [  
                "Authorization: Bearer { $apiToken }" ,  
                "Content-Type: application/json"  
            ],  
            'method'  =>  'POST' ,  
            'content'  =>  json_encode ( $payload )  
        ]  
    ];  
      
    $context  =  stream_context_create ( $options );  
    $result  =  file_get_contents ( $url ,  false ,  $context );  
      
    if  ( $result  ===  FALSE ) {  
        $error  =  error_get_last ();  
        throw  new  Exception ( "Failed to deploy flow: "  .  $error [ 'message' ]);  
    }  
      
    $httpCode  =  null ;  
    if  ( isset ( $http_response_header )) {  
        foreach  ( $http_response_header  as  $header ) {  
            if  ( strpos ( $header ,  'HTTP/' )  ===  0 ) {  
                $httpCode  =  ( int )  substr ( $header ,  9 ,  3 );  
                break ;  
            }  
        }  
    }  
      
    $response  =  json_decode ( $result ,  true );  
      
    if  ( $httpCode  !==  200 ) {  
        $errorMessage  =  $response [ 'detail' ]  ??  'Unknown error' ;  
        throw  new  Exception ( "Deployment failed: { $errorMessage }" );  
    }  
      
    return  $response ;  
}  
 
// Usage  
try  {  
    $result  =  deployFlow (  
        'my-rag-pipeline' ,  
        'YOUR_API_TOKEN' ,  
        'Advanced document analysis and Q&A system'  
    );  
      
    echo  "✅ Deployment successful! \n " ;  
    echo  "Revision ID: { $result ['revision_id']} \n " ;  
    echo  "Status: { $result ['status']} \n " ;  
    echo  "Message: { $result ['message']} \n " ;  
      
    $flowUrl  =  "https://my-rag-pipeline.flows.graphorlm.com" ;  
    echo  "🚀 Flow available at: { $flowUrl } \n " ;  
      
}  catch  ( Exception  $e ) {  
    echo  "❌ Deployment failed: "  .  $e -> getMessage ()  .  " \n " ;  
}  
?>  
 
Deployment Process  
The deployment process involves several steps: 
Validation : Checks if the flow exists and is properly configured 
Revision Creation : Creates a new revision with updated node IDs 
Graph Update : Updates the flow graph with the new revision 
Component Deployment : Deploys all flow components (dataset, chunking, retrieval, Response Node, etc.) 
Traffic Routing : Routes 100% of traffic to the new revision 
Status Update : Updates the flow status to “Deployed” 
 
Deployment can take several minutes depending on flow complexity and the number of components that need to be processed. 
 
Deployment Requirements  
Before deploying a flow, ensure: 
1. Flow Configuration  
✅ Flow has been created and saved 
✅ Response Node is configured and properly connected  
✅ All required components are configured 
✅ Dataset node has source documents selected 
✅ Response Node model and prompt configuration is complete and valid 
 
2. Source Documents  
✅ Documents are uploaded to the project 
✅ Documents are processed and in “Completed” status 
✅ At least one document is selected in dataset nodes 
 
3. Flow Components  
✅ All nodes have valid configurations 
✅ Node connections are properly established 
✅ Required parameters are set for each component 
 
4. API Access  
✅ Valid API token with deployment permissions 
✅ Flow name is unique and follows naming conventions 
 
Error Responses  
Common Error Codes  
Status Code Description Common Causes 400 Bad Request Invalid flow configuration, missing required components 401 Unauthorized Invalid or missing API token 404 Not Found Flow doesn’t exist or insufficient permissions 500 Internal Server Error Deployment process failed, infrastructure issues 
 
{  
  "detail" :  "Error message describing what went wrong"  
}  
 
Example Error Responses  
Flow Not Found  
{  
  "detail" :  "Flow with name 'my-rag-pipeline' not found"  
}  
 
Invalid Configuration  
{  
  "detail" :  "Flow configuration is invalid: Dataset node is missing source documents"  
}  
 
Deployment Failed  
{  
  "detail" :  "Failed to deploy flow: Component validation failed"  
}  
 
Missing Response Node  
{  
  "detail" :  "Failed to deploy flow: No Response Node found in flow"  
}  
 
Insufficient Permissions  
{  
  "detail" :  "You don't have permission to deploy flows in this project"  
}  
 
The tool_description parameter is used when your deployed flow is accessed via MCP (Model Context Protocol) or when it’s used as a tool in other systems. It helps describe what your flow does and how it should be used. 
Be Specific : Clearly describe what your flow does 
Include Use Cases : Mention what types of queries it handles best 
Mention Data Sources : Indicate what kind of documents or data it processes 
 
{  
  "tool_description" :  "Technical documentation Q&A system that searches through software manuals, API docs, and troubleshooting guides to provide accurate answers to development questions"  
}  
 
{  
  "tool_description" :  "Legal document analysis tool that processes contracts, regulations, and case studies to answer legal research questions with cited sources"  
}  
 
{  
  "tool_description" :  "Customer support knowledge base that searches through product manuals, FAQ documents, and support tickets to provide helpful customer service responses"  
}  
 
Integration Examples  
Automated Deployment Pipeline  
class  FlowDeploymentManager  {  
  constructor ( apiToken ) {  
    this . apiToken  =  apiToken ;  
  }  
 
  async  deployWithValidation ( flowName ,  toolDescription ) {  
    try  {  
      // Step 1: Validate flow configuration  
      console . log ( '📋 Validating flow configuration...' );  
      await  this . validateFlowConfiguration ( flowName );  
        
      // Step 2: Deploy the flow  
      console . log ( '🚀 Starting deployment...' );  
      const  result  =  await  this . deployFlow ( flowName ,  toolDescription );  
        
      // Step 3: Verify deployment  
      console . log ( '✅ Verifying deployment...' );  
      await  this . verifyDeployment ( flowName );  
        
      console . log ( '🎉 Deployment completed successfully!' );  
      return  result ;  
        
    }  catch  ( error ) {  
      console . error ( '❌ Deployment failed:' ,  error . message );  
      throw  error ;  
    }  
  }  
 
  async  deployFlow ( flowName ,  toolDescription ) {  
    const  url  =  `https:// ${ flowName } .flows.graphorlm.com/deploy` ;  
      
    const  payload  =  {};  
    if  ( toolDescription ) {  
      payload . tool_description  =  toolDescription ;  
    }  
 
    const  response  =  await  fetch ( url , {  
      method:  'POST' ,  
      headers:  {  
        'Authorization' :  `Bearer  ${ this . apiToken } ` ,  
        'Content-Type' :  'application/json' ,  
      },  
      body:  JSON . stringify ( payload )  
    });  
 
    if  ( ! response . ok ) {  
      const  errorData  =  await  response . json ();  
      throw  new  Error ( `Deployment failed:  ${ errorData . detail } ` );  
    }  
 
    return  await  response . json ();  
  }  
 
  async  validateFlowConfiguration ( flowName ) {  
    // Check if flow exists and is properly configured  
    // This would typically involve checking dataset nodes, Response Node, etc.  
    const  datasetsUrl  =  `https:// ${ flowName } .flows.graphorlm.com/datasets` ;  
      
    const  response  =  await  fetch ( datasetsUrl , {  
      headers:  {  
        'Authorization' :  `Bearer  ${ this . apiToken } ` ,  
      }  
    });  
 
    if  ( ! response . ok ) {  
      throw  new  Error ( 'Flow configuration validation failed' );  
    }  
 
    const  datasets  =  await  response . json ();  
    if  ( datasets . length  ===  0 ) {  
      throw  new  Error ( 'Flow has no dataset nodes configured' );  
    }  
 
    // Additional validation logic here  
    // You would also check for Response Node presence:  
    // const llmUrl = `https://${flowName}.flows.graphorlm.com/llm`;  
    // const llmResponse = await fetch(llmUrl, { headers: { 'Authorization': `Bearer ${this.apiToken}` }});  
    // const llmNodes = await llmResponse.json();  
    // if (llmNodes.length === 0) {  
    //   throw new Error('Flow has no Response Node configured');  
    // }  
      
    console . log ( '✅ Flow configuration is valid' );  
  }  
 
  async  verifyDeployment ( flowName ) {  
    // Test the deployed flow with a simple query  
    const  testUrl  =  `https:// ${ flowName } .flows.graphorlm.com` ;  
      
    const  response  =  await  fetch ( testUrl , {  
      method:  'POST' ,  
      headers:  {  
        'Authorization' :  `Bearer  ${ this . apiToken } ` ,  
        'Content-Type' :  'application/json' ,  
      },  
      body:  JSON . stringify ({  
        query:  'test query' ,  
        page_size:  1  
      })  
    });  
 
    if  ( ! response . ok ) {  
      throw  new  Error ( 'Deployment verification failed - flow is not responding' );  
    }  
 
    console . log ( '✅ Flow is responding correctly' );  
  }  
}  
 
// Usage  
const  deploymentManager  =  new  FlowDeploymentManager ( 'YOUR_API_TOKEN' );  
 
deploymentManager . deployWithValidation (  
  'my-rag-pipeline' ,  
  'Advanced technical documentation assistant'  
). then ( result  =>  {  
  console . log ( 'Deployment result:' ,  result );  
}). catch ( error  =>  {  
  console . error ( 'Deployment error:' ,  error );  
});  
 
Batch Deployment for Multiple Flows  
import  asyncio  
import  aiohttp  
import  json  
from  typing  import  List, Dict, Any  
 
class  BatchFlowDeployer :  
    def  __init__ ( self ,  api_token :  str ):  
        self .api_token  =  api_token  
          
    async  def  deploy_single_flow (  
        self ,   
        session : aiohttp.ClientSession,   
        flow_name :  str ,   
        tool_description :  str  =  None  
    ) -> Dict[ str , Any]:  
        url  =  f "https:// { flow_name } .flows.graphorlm.com/deploy"  
          
        payload  =  {}  
        if  tool_description:  
            payload[ "tool_description" ]  =  tool_description  
              
        headers  =  {  
            "Authorization" :  f "Bearer  { self .api_token } " ,  
            "Content-Type" :  "application/json"  
        }  
          
        try :  
            async  with  session.post(url,  headers = headers,  json = payload)  as  response:  
                if  response.status  ==  200 :  
                    result  =  await  response.json()  
                    return  {  
                        "flow_name" : flow_name,  
                        "status" :  "success" ,  
                        "revision_id" : result[ "revision_id" ],  
                        "message" : result[ "message" ]  
                    }  
                else :  
                    error_text  =  await  response.text()  
                    return  {  
                        "flow_name" : flow_name,  
                        "status" :  "error" ,  
                        "error" : error_text  
                    }  
        except  Exception  as  e:  
            return  {  
                "flow_name" : flow_name,  
                "status" :  "error" ,  
                "error" :  str (e)  
            }  
      
    async  def  deploy_multiple_flows (  
        self ,   
        flows : List[Dict[ str ,  str ]]  
    ) -> List[Dict[ str , Any]]:  
        """  
        Deploy multiple flows concurrently.  
          
        Args:  
            flows: List of dicts with 'name' and optional 'tool_description'  
        """  
        async  with  aiohttp.ClientSession()  as  session:  
            tasks  =  [  
                self .deploy_single_flow(  
                    session,   
                    flow[ "name" ],   
                    flow.get( "tool_description" )  
                )  
                for  flow  in  flows  
            ]  
            return  await  asyncio.gather( * tasks,  return_exceptions = True )  
 
# Usage  
async  def  deploy_all_flows ():  
    deployer  =  BatchFlowDeployer( "YOUR_API_TOKEN" )  
      
    flows_to_deploy  =  [  
        {  
            "name" :  "customer-support-flow" ,  
            "tool_description" :  "Customer support Q&A system"  
        },  
        {  
            "name" :  "technical-docs-flow" ,   
            "tool_description" :  "Technical documentation assistant"  
        },  
        {  
            "name" :  "legal-research-flow" ,  
            "tool_description" :  "Legal document research tool"  
        }  
    ]  
      
    print ( "🚀 Starting batch deployment..." )  
    results  =  await  deployer.deploy_multiple_flows(flows_to_deploy)  
      
    successful  =  0  
    failed  =  0  
      
    for  result  in  results:  
        if  isinstance (result,  dict ):  
            if  result[ "status" ]  ==  "success" :  
                print ( f "✅  { result[ 'flow_name' ] } :  { result[ 'message' ] } " )  
                successful  +=  1  
            else :  
                print ( f "❌  { result[ 'flow_name' ] } :  { result[ 'error' ] } " )  
                failed  +=  1  
        else :  
            print ( f "❌ Unexpected error:  { result } " )  
            failed  +=  1  
      
    print ( f " \n 📊 Deployment Summary:" )  
    print ( f "✅ Successful:  { successful } " )  
    print ( f "❌ Failed:  { failed } " )  
 
# Run batch deployment  
# asyncio.run(deploy_all_flows())  
 
Best Practices  
Pre-Deployment Checklist  
✅ Ensure Response Node is configured and connected  
✅ Test your flow configuration in the Graphor interface 
✅ Verify all documents are processed and available 
✅ Ensure dataset nodes have appropriate source selections 
✅ Test component configurations individually 
✅ Validate Response Node model, prompt, and API settings 
 
Deployment Strategy  
Start Small : Deploy simple flows first to validate the process 
Monitor Performance : Watch deployment progress and check for errors 
Version Control : Keep track of revision IDs for rollback if needed 
Gradual Rollout : Test thoroughly before production deployment 
 
Post-Deployment  
Verify Functionality : Test the deployed flow with sample queries 
Monitor Performance : Check response times and accuracy 
Update Documentation : Document the deployment and any custom configurations 
Set Up Monitoring : Implement logging and error tracking 
 
Security Considerations  
API Token Management : Use environment variables for tokens 
Access Control : Ensure only authorized users can deploy flows 
Network Security : Use HTTPS for all deployment requests 
Audit Trail : Keep logs of all deployments for compliance 
 
Troubleshooting  
Solution : Verify that:
The flow exists in your Graphor project 
The flow name in the URL exactly matches the flow name in the system 
Your API token has access to the correct project 
The flow has been saved properly in the flow builder 
 
Invalid Configuration Error
Solution : Check your flow configuration:
Ensure you have a Response Node configured in your flow  
Ensure all required nodes are present 
Verify dataset nodes have source documents selected 
Check that all node parameters are properly configured 
Validate Response Node model and prompt configuration 
Ensure all node connections are properly established 
 
Solution : For “No Response Node found” deployment errors:
Add a Response Node to your flow 
Configure the Response Node with a valid model and prompt 
Connect the Response Node properly to receive input from other nodes 
The Response Node is required to generate responses for deployed flows 
Ensure the Response Node is not disconnected from the flow 
 
Solution : For slow deployments:
Complex flows may take several minutes to deploy 
Check if large datasets are being processed 
Try deploying during off-peak hours 
Contact support if deployment consistently times out 
 
Solution : Verify your documents:
All documents are uploaded and processed 
Documents have “Completed” status in the sources list 
At least one document is selected in dataset nodes 
Documents are accessible and not corrupted 
 
Solution : Check your API authentication:
Verify API token is valid and not expired 
Ensure token has deployment permissions 
Check that token belongs to the correct project 
Regenerate token if necessary 
 
Solution : For deployment infrastructure issues:
Check Graphor status page for service incidents 
Try deployment again after a few minutes 
Simplify flow configuration if possible 
Contact support with revision ID if error persists 
  
Monitoring and Management  
After successful deployment, you can: 
Check Deployment Status  
Monitor flow execution through the Graphor dashboard 
Use the Run Flow endpoint  to test functionality 
Review logs and performance metrics 
 
Update Deployments  
Modify your flow configuration in the Graphor interface 
Deploy again to create a new revision 
Previous revisions are automatically replaced 
 
Rollback if Needed  
Contact support if you need to rollback to a previous revision 
Keep track of working revision IDs for reference 
 
Next Steps  
After successfully deploying your flow, you can: