mirror of https://github.com/daffainfo/nuclei.git
74 lines
2.4 KiB
Go
74 lines
2.4 KiB
Go
package http
|
|
|
|
import (
|
|
"github.com/projectdiscovery/nuclei/v2/pkg/protocols"
|
|
"github.com/projectdiscovery/nuclei/v2/pkg/protocols/common/generators"
|
|
)
|
|
|
|
// requestGenerator generates requests sequentially based on various
|
|
// configurations for a http request template.
|
|
//
|
|
// If payload values are present, an iterator is created for the payload
|
|
// values. Paths and Raw requests are supported as base input, so
|
|
// it will automatically select between them based on the template.
|
|
type requestGenerator struct {
|
|
currentIndex int
|
|
request *Request
|
|
options *protocols.ExecuterOptions
|
|
payloadIterator *generators.Iterator
|
|
}
|
|
|
|
// newGenerator creates a new request generator instance
|
|
func (r *Request) newGenerator() *requestGenerator {
|
|
generator := &requestGenerator{request: r, options: r.options}
|
|
|
|
if len(r.Payloads) > 0 {
|
|
generator.payloadIterator = r.generator.NewIterator()
|
|
}
|
|
return generator
|
|
}
|
|
|
|
// nextValue returns the next path or the next raw request depending on user input
|
|
// It returns false if all the inputs have been exhausted by the generator instance.
|
|
func (r *requestGenerator) nextValue() (value string, payloads map[string]interface{}, result bool) {
|
|
// If we have paths, return the next path.
|
|
if len(r.request.Path) > 0 && r.currentIndex < len(r.request.Path) {
|
|
if value := r.request.Path[r.currentIndex]; value != "" {
|
|
r.currentIndex++
|
|
return value, nil, true
|
|
}
|
|
}
|
|
|
|
// If we have raw requests, start with the request at current index.
|
|
// If we are not at the start, then check if the iterator for payloads
|
|
// has finished if there are any.
|
|
//
|
|
// If the iterator has finished for the current raw request
|
|
// then reset it and move on to the next value, otherwise use the last request.
|
|
if len(r.request.Raw) > 0 && r.currentIndex < len(r.request.Raw) {
|
|
if r.payloadIterator != nil {
|
|
payload, ok := r.payloadIterator.Value()
|
|
if !ok {
|
|
r.currentIndex++
|
|
r.payloadIterator.Reset()
|
|
|
|
// No more payloads request for us now.
|
|
if len(r.request.Raw) == r.currentIndex {
|
|
return "", nil, false
|
|
}
|
|
if item := r.request.Raw[r.currentIndex]; item != "" {
|
|
newPayload, ok := r.payloadIterator.Value()
|
|
return item, newPayload, ok
|
|
}
|
|
return "", nil, false
|
|
}
|
|
return r.request.Raw[r.currentIndex], payload, true
|
|
}
|
|
if item := r.request.Raw[r.currentIndex]; item != "" {
|
|
r.currentIndex++
|
|
return item, nil, true
|
|
}
|
|
}
|
|
return "", nil, false
|
|
}
|