Skip to content

Commit

Permalink
Merge pull request Lavanyasuc31#18 from Ayushi40804/ayushi40804
Browse files Browse the repository at this point in the history
Added my Fuzzing tool project in Go
  • Loading branch information
Lavanyasuc31 authored Oct 8, 2024
2 parents 1c3cea7 + 9421235 commit 335d6e6
Show file tree
Hide file tree
Showing 12 changed files with 417 additions and 0 deletions.
98 changes: 98 additions & 0 deletions Go/FuzzerBuzzer/README.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,98 @@
# FuzzerBuzzer

FuzzerBuzzer is a fuzzing tool designed to test web applications by sending random inputs to specified endpoints. This tool can help identify vulnerabilities and unexpected behavior in applications.

## Table of Contents

- [Features](#features)
- [Installation](#installation)
- [Usage](#usage)
- [Configuration](#configuration)
- [Testing](#testing)
- [Code Structure](#code-structure)

## Features

- Generate random strings and JSON data as input.
- Send fuzzed inputs to specified HTTP endpoints.
- Simple configuration via YAML file.

## Installation

To set up FuzzerBuzzer, follow these steps:

1. Clone the repository:
```bash
git clone https://github.com/Ayushi40804/Hacktoberfest2024.git
cd Hacktoberfest2024/FuzzerBuzzer
2. Ensure you have Go installed on your machine. If not, download and install it from https://golang.org.

3. Install necessary dependencies:

```bash
go mod tidy
```
## Usage
1. Start your target web application on http://localhost:8080/test. You can do to app directory and run app.go file.

```bash
go run app.go
```

2. Configure the fuzzer by editing the config/config.yaml file:

```yaml
target_url: "http://localhost:8080/test"
seed: 12345
```
3. Run the fuzzer:

```bash
go run cmd/fuzzer.go
```
## Configuration
The configuration file config/config.yaml should include the following fields:

- target_url: The URL to which the fuzzing requests will be sent.
- seed: An integer seed value for random number generation to ensure reproducibility.

Example configuration:

```yaml
target_url: "http://localhost:8080/test"
seed:12345
```

## Testing
To run tests for the FuzzerBuzzer:

1. Navigate to the tests directory:

```bash
cd tests
```
2. Execute the tests:

```bash
go test -v
```
## Code Structure
The project follows a modular structure:

```bash
FuzzerBuzzer/
├── cmd/
│ └── fuzzer.go # Main entry point for the fuzzer
├── config/
│ └── config.yaml # Configuration file
├── internal/
│ ├── fuzz_logic/
│ │ └── fuzz.go # Fuzzing logic and HTTP requests
│ └── generator/
│ └── input_gen.go # Input generation logic
├── pkg/
│ └── helpers.go # Utility functions (if any)
├── tests/
│ └── fuzzer_test.go # Test cases for the fuzzer
├── go.mod # Go module definition
└── README.md # Project documentation
28 changes: 28 additions & 0 deletions Go/FuzzerBuzzer/app/app.go
Original file line number Diff line number Diff line change
@@ -0,0 +1,28 @@
package main

import (
"fmt"
"net/http"
)

func main() {
http.HandleFunc("/test", testHandler)
fmt.Println("Server starting on :8080")
if err := http.ListenAndServe(":8080", nil); err != nil {
fmt.Println("Server error:", err)
}
}

func testHandler(w http.ResponseWriter, r *http.Request) {
r.ParseForm()
input := r.FormValue("input")

// Simple response based on input
if input == "" {
http.Error(w, "No input provided", http.StatusBadRequest)
return
}

response := fmt.Sprintf("Received input: %s", input)
w.Write([]byte(response))
}
43 changes: 43 additions & 0 deletions Go/FuzzerBuzzer/cmd/fuzzer.go
Original file line number Diff line number Diff line change
@@ -0,0 +1,43 @@
package main

import (
"log"
"os"

"github.com/Ayushi40804/Hacktoberfest2024/FuzzerBuzzer/internal/fuzz_logic"
"github.com/Ayushi40804/Hacktoberfest2024/FuzzerBuzzer/internal/generator"
"gopkg.in/yaml.v2"
)

type Config struct {
TargetURL string `yaml:"target_url"`
Seed int64 `yaml:"seed"`
}

func main() {
// Load the configuration
config, err := loadConfig("config/config.yaml")
if err != nil {
log.Fatalf("Error reading config file: %v", err)
}

// Create an InputGenerator
inputGen := generator.NewInputGenerator(config.Seed)

// Create a Fuzzer
fuzzer := fuzz_logic.NewFuzzer(config.TargetURL, inputGen)

// Start the fuzzing process
fuzzer.Start()
}

// loadConfig loads the configuration from a YAML file
func loadConfig(path string) (Config, error) {
var config Config
data, err := os.ReadFile(path)
if err != nil {
return config, err
}
err = yaml.Unmarshal(data, &config)
return config, err
}
2 changes: 2 additions & 0 deletions Go/FuzzerBuzzer/config/config.yaml
Original file line number Diff line number Diff line change
@@ -0,0 +1,2 @@
target_url: "http://localhost:8080/test"
seed: 12345
6 changes: 6 additions & 0 deletions Go/FuzzerBuzzer/go.mod
Original file line number Diff line number Diff line change
@@ -0,0 +1,6 @@
module github.com/Ayushi40804/Hacktoberfest2024/FuzzerBuzzer


go 1.23.2

require gopkg.in/yaml.v2 v2.4.0
4 changes: 4 additions & 0 deletions Go/FuzzerBuzzer/go.sum
Original file line number Diff line number Diff line change
@@ -0,0 +1,4 @@
gopkg.in/check.v1 v0.0.0-20161208181325-20d25e280405 h1:yhCVgyC4o1eVCa2tZl7eS0r+SDo693bJlVdllGtEeKM=
gopkg.in/check.v1 v0.0.0-20161208181325-20d25e280405/go.mod h1:Co6ibVJAznAaIkqp8huTwlJQCZ016jof/cbN4VW5Yz0=
gopkg.in/yaml.v2 v2.4.0 h1:D8xgwECY7CYvx+Y2n4sBz93Jn9JRvxdiyyo8CTfuKaY=
gopkg.in/yaml.v2 v2.4.0/go.mod h1:RDklbk79AGWmwhnvt/jBztapEOGDOx6ZbXqjP6csGnQ=
39 changes: 39 additions & 0 deletions Go/FuzzerBuzzer/internal/fuzz_logic/fuzz.go
Original file line number Diff line number Diff line change
@@ -0,0 +1,39 @@
package fuzz_logic

import (
"fmt"
"net/http"

"github.com/Ayushi40804/Hacktoberfest2024/FuzzerBuzzer/internal/generator"
)

// Fuzzer struct represents the fuzzer with necessary fields
type Fuzzer struct {
TargetURL string
Generator *generator.InputGenerator
}

// NewFuzzer creates a new Fuzzer instance
func NewFuzzer(targetURL string, generator *generator.InputGenerator) *Fuzzer {
return &Fuzzer{
TargetURL: targetURL,
Generator: generator,
}
}

// Start method to begin fuzzing process
func (f *Fuzzer) Start() {
// Generate random input
randomInput := f.Generator.GenerateRandomString(10)
fmt.Println("Generated input:", randomInput)

// Send a POST request
resp, err := http.Post(f.TargetURL+"?input="+randomInput, "application/json", nil)
if err != nil {
fmt.Println("Error sending request:", err)
return
}
defer resp.Body.Close()

fmt.Println("Response Status:", resp.Status)
}
49 changes: 49 additions & 0 deletions Go/FuzzerBuzzer/internal/generator/input_gen.go
Original file line number Diff line number Diff line change
@@ -0,0 +1,49 @@
package generator

import (
"encoding/json"
"math/rand"
)

// InputGenerator struct for generating various types of input
type InputGenerator struct {
Seed int64
}

// NewInputGenerator creates a new InputGenerator with a specified seed
func NewInputGenerator(seed int64) *InputGenerator {
rand.Seed(seed) // Seed the random number generator
return &InputGenerator{Seed: seed}
}

// GenerateRandomString generates a random string of a specified length
func (ig *InputGenerator) GenerateRandomString(length int) string {
letters := []rune("abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ0123456789")
result := make([]rune, length)
for i := range result {
result[i] = letters[rand.Intn(len(letters))]
}
return string(result)
}

// GenerateRandomJSON generates random JSON input
func (ig *InputGenerator) GenerateRandomJSON() string {
type RandomData struct {
Name string `json:"name"`
Email string `json:"email"`
Age int `json:"age"`
}

data := RandomData{
Name: ig.GenerateRandomString(10),
Email: ig.GenerateRandomString(5) + "@example.com",
Age: rand.Intn(100),
}

// Convert to JSON
jsonData, err := json.Marshal(data)
if err != nil {
return "{}" // Return empty JSON on error
}
return string(jsonData)
}
47 changes: 47 additions & 0 deletions Go/FuzzerBuzzer/internal/http/client.go
Original file line number Diff line number Diff line change
@@ -0,0 +1,47 @@
package http

import (
"fmt"
"io"
"net/http"
)

// Client struct that wraps the http.Client and any custom configurations
type Client struct {
HTTPClient *http.Client
Headers map[string]string
}

// NewClient creates a new HTTP client with custom headers

func NewClient(headers map[string]string) *http.Client {

client := &http.Client{}

// You can add custom headers handling logic here if needed

return client

}

// Post sends a POST request to the specified URL with the provided data
func (c *Client) Post(url string, contentType string, body io.Reader) (*http.Response, error) {
// Create a new request
req, err := http.NewRequest("POST", url, body)
if err != nil {
return nil, fmt.Errorf("failed to create request: %w", err)
}

// Add custom headers to the request
for key, value := range c.Headers {
req.Header.Set(key, value)
}

// Send the request
resp, err := c.HTTPClient.Do(req)
if err != nil {
return nil, fmt.Errorf("failed to send request: %w", err)
}

return resp, nil
}
33 changes: 33 additions & 0 deletions Go/FuzzerBuzzer/internal/http/errors.go
Original file line number Diff line number Diff line change
@@ -0,0 +1,33 @@
package http

import (
"fmt"
"net/http"
)

// HTTPError represents an error that occurred during an HTTP request
type HTTPError struct {
StatusCode int
Message string
}

// Error implements the error interface for HTTPError
func (e *HTTPError) Error() string {
return fmt.Sprintf("HTTP %d: %s", e.StatusCode, e.Message)
}

// NewHTTPError creates a new instance of HTTPError
func NewHTTPError(statusCode int, message string) *HTTPError {
return &HTTPError{
StatusCode: statusCode,
Message: message,
}
}

// CheckResponse checks the HTTP response and returns an error if the status code indicates failure
func CheckResponse(resp *http.Response) error {
if resp.StatusCode < 200 || resp.StatusCode >= 300 {
return NewHTTPError(resp.StatusCode, http.StatusText(resp.StatusCode))
}
return nil
}
Loading

0 comments on commit 335d6e6

Please sign in to comment.