Added the workspace name in the scanning endpoint

This commit is contained in:
j3ssie
2025-08-08 21:15:31 +08:00
parent 36b1a5aad0
commit 6f7271fa49
5 changed files with 496 additions and 18 deletions
+6 -1
View File
@@ -148,6 +148,12 @@ func ParseInputFormat(raw string, options libs.Options) map[string]string {
// ParseInput parse input for routine
func ParseInput(raw string, options libs.Options) map[string]string {
ROptions := ParseTarget(raw)
if utils.IsFile(raw) {
ROptions["TargetIsFile"] = "true"
} else {
ROptions["TargetIsFile"] = "false"
}
if options.EnableFormatInput {
// avoid the loophole
options.EnableFormatInput = false
@@ -199,7 +205,6 @@ func ParseInput(raw string, options libs.Options) map[string]string {
ROptions["Workspace"] = utils.CleanPath(options.Scan.CustomWorkspace)
}
ROptions["Output"] = path.Join(ROptions["Workspaces"], ROptions["Workspace"])
ROptions["ExecutionLog"] = path.Join(ROptions["Output"], "execution.log")
ROptions["LogFile"] = options.LogFile
+1 -1
View File
@@ -4,7 +4,7 @@ import "fmt"
const (
// VERSION of this project
VERSION = "v4.7.0"
VERSION = "v4.7.1"
// DESC description of the tool
DESC = "A Workflow Engine for Offensive Security"
// BINARY name of osmedeus
+457
View File
@@ -0,0 +1,457 @@
# Osmedeus API Specification
> Generated by LLM
- [Osmedeus API Specification](#osmedeus-api-specification)
- [Overview](#overview)
- [Base URL](#base-url)
- [Authentication](#authentication)
- [1. JWT Token Authentication (Default)](#1-jwt-token-authentication-default)
- [2. Basic Authentication (Optional)](#2-basic-authentication-optional)
- [3. No Authentication (Development Mode)](#3-no-authentication-development-mode)
- [API Endpoints](#api-endpoints)
- [Authentication](#authentication-1)
- [Login](#login)
- [System Health](#system-health)
- [Health Check](#health-check)
- [Ping](#ping)
- [Workspaces](#workspaces)
- [List All Workspaces](#list-all-workspaces)
- [Get Workspace Details](#get-workspace-details)
- [Delete Workspace](#delete-workspace)
- [Scans](#scans)
- [List All Scans](#list-all-scans)
- [Start New Scan](#start-new-scan)
- [Processes](#processes)
- [List Running Processes](#list-running-processes)
- [Workflows](#workflows)
- [List Available Workflows](#list-available-workflows)
- [File Operations](#file-operations)
- [Upload Data](#upload-data)
- [Static Content](#static-content)
- [Workspace Files](#workspace-files)
- [Storage Files](#storage-files)
- [Utility](#utility)
- [Raw Directory Information](#raw-directory-information)
- [Helper Message](#helper-message)
- [Example Scanning request](#example-scanning-request)
- [Basic Scanning](#basic-scanning)
- [Scanning with URL workflow](#scanning-with-url-workflow)
## Overview
Osmedeus is a workflow engine for offensive security testing. This API provides endpoints to manage workspaces, execute scans, and monitor processes.
## Base URL
- **Local**: `http://localhost:8000`
- **With SSL**: `https://localhost:8443`
## Authentication
The API supports two authentication methods:
### 1. JWT Token Authentication (Default)
- **Login Endpoint**: `POST /api/login`
- **Token Header**: `Authorization: Osmedeus <token>`
- **Token Expiry**: 30 days
### 2. Basic Authentication (Optional)
- **Username**: `osmedeus`
- **Password**: Configured master password
- **Header**: `Authorization: Basic <base64(username:password)>`
### 3. No Authentication (Development Mode)
- Enabled with `-A` flag
## API Endpoints
### Authentication
#### Login
Authenticate user and obtain JWT token.
**Endpoint**: `POST /api/login`
**Request Body**:
```json
{
"username": "admin",
"password": "your_password"
}
```
**Response**:
```json
{
"status": "success",
"message": "Successfully login",
"token": "eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9..."
}
```
**Status Codes**:
- `200`: Success
- `401`: Unauthorized
- `500`: Internal Server Error
### System Health
#### Health Check
Check server health status and version.
**Endpoint**: `GET /api/osmp/health`
**Response**:
```json
{
"status": 200,
"data": {
"version": "v4.5.0"
},
"message": "server is up"
}
```
#### Ping
Simple connectivity check.
**Endpoint**: `GET /ping`
**Response**:
```json
{
"status": 200,
"message": "pong"
}
```
### Workspaces
#### List All Workspaces
Get all available workspaces.
**Endpoint**: `GET /api/osmp/workspaces`
**Response**:
```json
{
"status": 200,
"data": [...],
"type": "workspaces",
"total": 42,
"message": "List all of Workspaces"
}
```
#### Get Workspace Details
Get detailed information about a specific workspace including reports.
**Endpoint**: `GET /api/osmp/workspace/{wsname}`
**Path Parameters**:
- `wsname` (string): Workspace name
**Response**:
```json
{
"status": 200,
"data": {
"workspace": {...},
"reports": {
"subdomain": ["/static/workspaces/target/subdomain.txt"],
"portscan": ["/static/workspaces/target/portscan.html"]
}
},
"type": "workspace",
"message": "Workspace Detail"
}
```
#### Delete Workspace
Delete a workspace and all its associated files.
**Endpoint**: `DELETE /api/osmp/delete/{wsname}`
**Path Parameters**:
- `wsname` (string): Workspace name
**Response**:
```json
{
"status": 200,
"type": "delete",
"message": "Workspace Deleted"
}
```
**Status Codes**:
- `200`: Success
- `400`: Workspace doesn't exist
### Scans
#### List All Scans
Get all running and completed scan processes.
**Endpoint**: `GET /api/osmp/scans`
**Response**:
```json
{
"status": 200,
"data": [...],
"type": "scans",
"total": 15,
"message": "List all the scan process"
}
```
#### Start New Scan
Execute a new scan with specified configuration.
**Endpoint**: `POST /api/osmp/execute`
**Request Body**:
```json
{
"target": "example.com",
"workflow": "general",
"workspace": "my-project",
"threads": 10,
"timeout": "1h",
"debug": false
}
```
**Advanced Request Examples**:
**Single Target**:
```json
{
"target": "example.com",
"workflow": "general"
}
```
**Multiple Targets**:
```json
{
"targets": ["1.2.3.4/24", "5.6.7.8/24"],
"as_file": true,
"workflow": "cidr"
}
```
**With Custom Parameters**:
```json
{
"target": "example.com",
"workflow": "general",
"params": ["-deep", "-aggressive"],
"distributed": true,
"concurrency": 5
}
```
**Response**:
```json
{
"status": 200,
"data": {
"command": "osmedeus scan -f general -t example.com -w my-project",
"input": "example.com",
"workspace": "my-project"
},
"type": "new-scan",
"message": "New Scan Imported"
}
```
**Request Schema**:
- `target` (string): Target to scan
- `targets` (array): List of targets to scan (optional)
- `workflow` (string): Workflow name to execute (default: "general")
- `workspace` (string): Workspace name (optional)
- `module` (string): Plugin name to run (optional)
- `threads` (integer): Number of concurrent threads (optional)
- `timeout` (string): Scan timeout (e.g., "1h", "30m") (optional)
- `concurrency` (integer): Concurrency level (optional)
- `distributed` (boolean): Enable distributed scanning (optional)
- `params` (array): Additional parameters (optional)
- `debug` (boolean): Enable debug mode (optional)
- `test` (boolean): Test mode without actual execution (optional)
### Processes
#### List Running Processes
Get all currently running Osmedeus processes.
**Endpoint**: `GET /api/osmp/ps`
**Response**:
```json
{
"status": 200,
"data": [...],
"type": "processes",
"total": 5,
"message": "List all osm process"
}
```
### Workflows
#### List Available Workflows
Get all available workflow configurations and their modules.
**Endpoint**: `GET /api/osmp/flows`
**Response**:
```json
{
"status": 200,
"data": [
{
"name": "general",
"desc": "General reconnaissance workflow",
"modules": "subdomain,portscan,vulnscan"
}
],
"total": 12,
"type": "flows",
"message": "Workflows Listing"
}
```
### File Operations
#### Upload Data
Upload target data or configuration files.
**Endpoint**: `POST /api/osmp/upload`
**Request Body**:
```json
{
"data": "example.com\nsub.example.com",
"filename": "targets.txt"
}
```
**Response**:
```json
{
"status": 200,
"data": {
"filepath": "/tmp/osmedeus-input/targets.txt"
},
"type": "upload",
"message": "New Data Uploaded"
}
```
### Static Content
#### Workspace Files
Access workspace files and reports.
**Endpoint**: `GET /{static_prefix}/workspaces/{path...}`
**Example**: `GET /static/workspaces/target/subdomain.txt`
#### Storage Files
Access storage files and configurations.
**Endpoint**: `GET /{static_prefix}/storages/{path...}`
**Example**: `GET /static/storages/cloud-configs/aws.json`
### Utility
#### Raw Directory Information
Get raw directory structure for workspaces, storages, and logs.
**Endpoint**: `GET /api/osmp/raw`
**Response**:
```json
{
"status": 200,
"data": {
"storages": "/static/storages/",
"workspaces": "/static/workspaces/",
"logs": "/static/logs/"
},
"type": "raw",
"message": "Raw directory"
}
```
#### Helper Message
Get help information and documentation links.
**Endpoint**: `GET /api/osmp/help`
**Response**:
```json
{
"status": 200,
"data": {
"version": "v4.5.0",
"doc": "https://docs.osmedeus.org",
"message": "[*] Visit this page for complete Usage: https://docs.osmedeus.org"
},
"type": "helper",
"message": "Helper message"
}
```
## Example Scanning request
### Basic Scanning
```
POST /api/osmp/execute HTTP/1.1
Host: 127.0.0.1:8000
User-Agent: curl/8.7.1
Accept: */*
Connection: keep-alive
Authorization: <your-auth>
Content-Type: application/json
Content-Length: 334
{
"target":"sample.io",
"flow":"general"
}
```
### Scanning with URL workflow
```
POST /api/osmp/execute HTTP/1.1
Host: 127.0.0.1:8000
User-Agent: curl/8.7.1
Accept: */*
Connection: keep-alive
Authorization: <your-auth>
Content-Type: application/json
Content-Length: 334
{
"targets": [
"origin-lite-www.example.com",
"partner.example.com",
"partners.example.com",
"polri.example.com",
"retailenabler.example.com",
"seller-id.example.com",
"shop-id.example.com",
"sobat.example.com"
],
"as_file": true,
"debug": true,
"workspace": "custom-workspace",
"workflow": "url"
}
```
+14 -1
View File
@@ -130,12 +130,19 @@ func CommandBuilder(taskData *TaskData) string {
return taskData.Command
}
// mean general scan
// mean general scan with -f
if taskData.ModuleName == "" {
command = fmt.Sprintf("%v %v -t %v %v%v%v%v", binary, workflow, taskData.Target, concurrency, timeout, workspace, params)
// this means loop through targets file one by one
if taskData.TargetsFile != "" {
command = fmt.Sprintf("%v %v -T %v %v%v%v%v", binary, workflow, taskData.TargetsFile, concurrency, timeout, workspace, params)
}
if taskData.TargetAsFile {
command = fmt.Sprintf("%v %v -t %v %v%v%v%v", binary, workflow, taskData.TargetsFile, concurrency, timeout, workspace, params)
}
command = strings.TrimSpace(command)
if taskData.Debug {
command = command + " --debug"
@@ -144,10 +151,16 @@ func CommandBuilder(taskData *TaskData) string {
}
command = fmt.Sprintf("%v %v -t %v %v %v%v%v%v", binary, plugin, taskData.Target, scanID, concurrency, timeout, workspace, params)
// this means loop through targets file one by one
if taskData.TargetsFile != "" {
command = fmt.Sprintf("%v %v -t %v %v %v%v%v%v", binary, plugin, taskData.TargetsFile, scanID, concurrency, timeout, workspace, params)
}
if taskData.TargetAsFile {
command = fmt.Sprintf("%v %v -t %v %v%v%v%v", binary, workflow, taskData.TargetsFile, concurrency, timeout, workspace, params)
}
command = strings.TrimSpace(command)
if taskData.Debug {
command = command + " --debug"
+18 -15
View File
@@ -16,19 +16,21 @@ type TaskData struct {
TargetsList []string `json:"targets" description:"List of targets to scan (optional)"`
WorkFlow string `json:"workflow" example:"general" description:"Workflow name to execute"`
ModuleName string `json:"module" example:"subdomain" description:"Plugin name to run (optional)"`
Workspace string `json:"workspace" example:"my-project" description:"Workspace name (optional)"`
TargetsFile string `json:"targets_file" example:"/path/to/targets.txt" description:"File containing targets (optional)"`
Threads int `json:"threads" example:"10" description:"Number of concurrent threads (optional)"`
Chunk bool `json:"chunk" example:"false" description:"Enable chunk mode (optional)"`
TargetAsFile bool `json:"as_file" example:"false" description:"Treat target as file (optional)"`
Params []string `json:"params" example:"[\"-deep\", \"-aggressive\"]" description:"Additional parameters (optional)"`
Timeout string `json:"timeout" example:"1h" description:"Scan timeout (optional)"`
Concurrency int `json:"concurrency" example:"5" description:"Concurrency level (optional)"`
Distributed bool `json:"distributed" example:"false" description:"Enable distributed scanning (optional)"`
WildCard bool `json:"wildcard" example:"false" description:"Enable wildcard mode (optional)"`
Debug bool `json:"debug" example:"false" description:"Enable debug mode (optional)"`
Test bool `json:"test" example:"false" description:"Test mode without actual execution (optional)"`
TargetAsFile bool `json:"as_file" example:"false" description:"Treat target as file (optional)"`
TargetsFile string `json:"targets_file" example:"/path/to/targets.txt" description:"File containing targets (optional)"`
UploadTargetFile bool `json:"upload_targets_file" example:"false" description:"Upload target data (optional)"`
Params []string `json:"params" example:"[\"-deep\", \"-aggressive\"]" description:"Additional parameters (optional)"`
ModuleName string `json:"module" example:"subdomain" description:"Plugin name to run (optional)"`
Workspace string `json:"workspace" example:"my-project" description:"Workspace name (optional)"`
Threads int `json:"threads" example:"10" description:"Number of concurrent threads (optional)"`
Chunk bool `json:"chunk" example:"false" description:"Enable chunk mode (optional)"`
Timeout string `json:"timeout" example:"1h" description:"Scan timeout (optional)"`
Concurrency int `json:"concurrency" example:"5" description:"Concurrency level (optional)"`
Distributed bool `json:"distributed" example:"false" description:"Enable distributed scanning (optional)"`
WildCard bool `json:"wildcard" example:"false" description:"Enable wildcard mode (optional)"`
Debug bool `json:"debug" example:"false" description:"Enable debug mode (optional)"`
Test bool `json:"test" example:"false" description:"Test mode without actual execution (optional)"`
}
// @Summary Start a new scan
@@ -87,8 +89,9 @@ func NewScan(c *fiber.Ctx) error {
return c.JSON(ResponseHTTP{
Status: 200,
Data: fiber.Map{
"command": taskData.Command,
"input": taskData.Target,
"command": taskData.Command,
"input": taskData.Target,
"workspace": taskData.Workspace, // this would be the folder name
},
Type: "new-scan",
Message: "New Scan Imported",