yaml
type: "io.kestra.plugin.scripts.python.script"
yaml
id: python_demo
namespace: company.team

tasks:
  - id: python
    type: io.kestra.plugin.scripts.python.Script
    dependencies:
      - requests
      - kestra
    script: |
      from kestra import Kestra
      import requests

      response = requests.get('https://kestra.io')
      print(response.status_code)

      Kestra.outputs({'status': response.status_code, 'text': response.text})

yaml
id: pip_packages_docker
namespace: company.team

tasks:
  - id: run_python
    type: io.kestra.plugin.scripts.python.Script
    dependencies:
      - requests
    script: |
      import requests
      import json

      response = requests.get("https://api.github.com")
      data = response.json()
      print(data)

yaml
id: python_logs
namespace: company.team

tasks:
  - id: python_logger
    type: io.kestra.plugin.scripts.python.Script
    allowFailure: true
    dependencies
      - kestra
    script: |
      import time
      from kestra import Kestra

      logger = Kestra.logger()

      logger.debug("DEBUG is used for diagnostic info.")
      time.sleep(0.5)

      logger.info("INFO confirms normal operation.")
      time.sleep(0.5)

      logger.warning("WARNING signals something unexpected.")
      time.sleep(0.5)

      logger.error("ERROR indicates a serious issue.")
      time.sleep(0.5)

      logger.critical("CRITICAL means a severe failure.")

yaml
id: pass_data_between_tasks
namespace: company.team

tasks:
  - id: download
    type: io.kestra.plugin.core.http.Download
    uri: https://huggingface.co/datasets/kestra/datasets/raw/main/csv/orders.csv

  - id: python
    type: io.kestra.plugin.scripts.python.Script
    script: |
      with open('{{ outputs.download.uri }}', 'r') as f:
        print(f.read())

yaml
id: python_output_file
namespace: company.team

tasks:
  - id: python
    type: io.kestra.plugin.scripts.python.Script
    outputFiles:
      - "myfile.txt"
    script: |
      f = open("myfile.txt", "a")
      f.write("Hello from a Kestra task!")
      f.close()

yaml
id: python_outputs
namespace: company.team

tasks:
  - id: clean_dataset
    type: io.kestra.plugin.scripts.python.Script
    containerImage: ghcr.io/kestra-io/pydata:latest
    outputFiles:
      - "clean_dataset.csv"
    dependencies:
      - pandas
    script: |
      import pandas as pd
      df = pd.read_csv("https://huggingface.co/datasets/kestra/datasets/raw/main/csv/messy_dataset.csv")

      # Replace non-numeric age values with NaN
      df["Age"] = pd.to_numeric(df["Age"], errors="coerce")

      # mean imputation: fill NaN values with the mean age
      mean_age = int(df["Age"].mean())
      print(f"Filling NULL values with mean: {mean_age}")
      df["Age"] = df["Age"].fillna(mean_age)
      df.to_csv("clean_dataset.csv", index=False)

  - id: read_file_from_python
    type: io.kestra.plugin.scripts.shell.Commands
    taskRunner:
      type: io.kestra.plugin.core.runner.Process
    commands:
      - head -n 10 {{ outputs.clean_dataset.outputFiles['clean_dataset.csv'] }}

yaml
id: python_use_input_in_inline
namespace: company.team

inputs:
  - id: pokemon
    type: STRING
    defaults: pikachu

  - id: your_age
    type: INT
    defaults: 25

tasks:
  - id: inline_script
    type: io.kestra.plugin.scripts.python.Script
    description: Fetch the pokemon detail and compare its experience
    containerImage: ghcr.io/kestra-io/pydata:latest
    dependencies:
      - requests
    script: |
      import requests
      import json

      url = "https://pokeapi.co/api/v2/pokemon/{{ inputs.pokemon }}"
      response = requests.get(url)

      if response.status_code == 200:
          pokemon = json.loads(response.text)
          print(f"Base experience of {{ inputs.pokemon }} is { pokemon.get('base_experience') }")
          if pokemon.get('base_experience') > int("{{ inputs.your_age }}"):
              print("{{ inputs.pokemon }} has more base experience than your age")
          else:
              print("{{ inputs.pokemon}} is too young!")
      else:
          print(f"Failed to retrieve the webpage. Status code: {response.status_code}")

yaml
id: python_input_file
namespace: company.team

tasks:
  - id: download_file
    type: io.kestra.plugin.core.http.Download
    uri: https://huggingface.co/datasets/kestra/datasets/raw/main/csv/orders.csv

  - id: get_total_rows
    type: io.kestra.plugin.scripts.python.Script
    dependencies:
      - pandas
    inputFiles:
      input.csv: "{{ outputs.download_file.uri }}"
    script: |
      import pandas as pd

      # Path to your CSV file
      csv_file_path = "input.csv"

      # Read the CSV file using pandas
      df = pd.read_csv(csv_file_path)

      # Get the number of rows
      num_rows = len(df)

      print(f"Number of rows: {num_rows}")

yaml
id: python_generate_outputs
namespace: company.team

tasks:
  - id: generate_output
    type: io.kestra.plugin.scripts.python.Script
    packageManager: PIP
    dependencies:
      - kestra
    script: |
      from kestra import Kestra

      marks = [79, 91, 85, 64, 82]
      Kestra.outputs({"total_marks": sum(marks),"average_marks": sum(marks)/len(marks)})

  - id: log_result
    type: io.kestra.plugin.core.log.Log
    message:
      - "Total Marks: {{ outputs.generate_output.vars.total_marks }}"
      - "Average Marks: {{ outputs.generate_output.vars.average_marks }}"
Properties
SubType string
Default python:3.13-slim
SubType string
SubType string
Default true
SubType string
Default ["/bin/sh","-c"]
SubType string
Default UV
Possible Values
PIPUV
Default AUTO
Possible Values
LINUXWINDOWSAUTO
Default 0
SubType string
Default busybox
Default true
SubType string
Default false
Default OVERWRITE
Possible Values
OVERWRITEFAILWARNIGNORE
SubType string
SubType string
Default ["{{flow.namespace}}"]
Default true
Default { "image": "busybox" }
Default default
Default ALWAYS
Possible Values
IF_NOT_PRESENTALWAYSNEVER
Default true
Validation RegExp \d+\.\d+\.\d+(-[a-zA-Z0-9-]+)?|([a-zA-Z0-9]+)
Default PT5S
Format duration
Default PT1H
Format duration
Default PT10M
Format duration
Default PT5S
Format duration
Default true
Default true
Default false
Validation RegExp \d+\.\d+\.\d+(-[a-zA-Z0-9-]+)?|([a-zA-Z0-9]+)
Default PT1H
Format duration
SubType integer
Default PT5S
Format duration
Default true
Default true
SubType string
Default ["https://www.googleapis.com/auth/cloud-platform"]
Validation RegExp \d+\.\d+\.\d+(-[a-zA-Z0-9-]+)?|([a-zA-Z0-9]+)
Default PT5S
Format duration
Default PT1H
Format duration
Possible Values
ACTION_UNSPECIFIEDRETRY_TASKFAIL_TASKUNRECOGNIZED
Default v1
Default RSA
Default https://kubernetes.default.svc
Validation RegExp \d+\.\d+\.\d+(-[a-zA-Z0-9-]+)?|([a-zA-Z0-9]+)
Default PT5S
Format duration
Default true
SubType string
Default e2-medium
Default 2
Minimum >= 0
Maximum <= 10
Default true
SubType string
Default ["https://www.googleapis.com/auth/cloud-platform"]
Validation RegExp \d+\.\d+\.\d+(-[a-zA-Z0-9-]+)?|([a-zA-Z0-9]+)
Default PT5S
Format duration
Default PT1H
Format duration
Min length 1
SubType
SubType string
SubType string
Default IF_NOT_PRESENT
Possible Values
IF_NOT_PRESENTALWAYSNEVER
SubType string
Default true
SubType
SubType string
Default [ "" ]
SubType string
Default VOLUME
Possible Values
MOUNTVOLUME
Default PT0S
Format duration
SubType string
Default IF_NOT_PRESENT
Possible Values
IF_NOT_PRESENTALWAYSNEVER
Validation RegExp \d+\.\d+\.\d+(-[a-zA-Z0-9-]+)?|([a-zA-Z0-9]+)
SubType string
Default true
SubType array
SubType string
SubType string
Default PT5S
Format duration
Default true
Default { "request": { "memory": "2048", "cpu": "1" } }
Default true
Default PT15M
Format duration
Validation RegExp \d+\.\d+\.\d+(-[a-zA-Z0-9-]+)?|([a-zA-Z0-9]+)
Default PT1H
Format duration