Struct goose::GooseAttack[][src]

pub struct GooseAttack { /* fields omitted */ }
Expand description

Global internal state for the load test.

Implementations

Goose’s internal global state.

Load configuration and initialize a GooseAttack.

Example
use goose::prelude::*;

let mut goose_attack = GooseAttack::initialize();

Initialize a GooseAttack with an already loaded configuration.

This is generally used by Worker instances and tests.

Example
use goose::GooseAttack;
use goose::config::GooseConfiguration;
use gumdrop::Options;

let configuration = GooseConfiguration::parse_args_default_or_exit();
let mut goose_attack = GooseAttack::initialize_with_config(configuration);

Define the order GooseTaskSets are allocated to new GooseUsers as they are launched.

By default, GooseTaskSets are allocated to new GooseUsers in a round robin style. For example, if TaskSet A has a weight of 5, TaskSet B has a weight of 3, and you launch 20 users, they will be launched in the following order: A, B, A, B, A, B, A, A, A, B, A, B, A, B, A, A, A, B, A, B

Note that the following pattern is repeated: A, B, A, B, A, B, A, A

If reconfigured to schedule serially, then they will instead be allocated in the following order: A, A, A, A, A, B, B, B, A, A, A, A, A, B, B, B, A, A, A, A

In the serial case, the following pattern is repeated: A, A, A, A, A, B, B, B

In the following example, GooseTaskSets are allocated to launching GooseUsers in a random order. This means running the test multiple times can generate different amounts of load, as depending on your weighting rules you may have a different number of GooseUsers running each GooseTaskSet each time.

Example
use goose::prelude::*;

#[tokio::main]
async fn main() -> Result<(), GooseError> {
    GooseAttack::initialize()?
        .set_scheduler(GooseScheduler::Random)
        .register_taskset(taskset!("A Tasks")
            .set_weight(5)?
            .register_task(task!(a_task_1))
        )
        .register_taskset(taskset!("B Tasks")
            .set_weight(3)?
            .register_task(task!(b_task_1))
        );

    Ok(())
}

async fn a_task_1(user: &mut GooseUser) -> GooseTaskResult {
    let _goose = user.get("/foo").await?;

    Ok(())
}

async fn b_task_1(user: &mut GooseUser) -> GooseTaskResult {
    let _goose = user.get("/bar").await?;

    Ok(())
}

A load test must contain one or more GooseTaskSets be registered into Goose’s global state with this method for it to run.

Example
use goose::prelude::*;

#[tokio::main]
async fn main() -> Result<(), GooseError> {
    GooseAttack::initialize()?
        .register_taskset(taskset!("ExampleTasks")
            .register_task(task!(example_task))
        )
        .register_taskset(taskset!("OtherTasks")
            .register_task(task!(other_task))
        );

    Ok(())
}

async fn example_task(user: &mut GooseUser) -> GooseTaskResult {
    let _goose = user.get("/foo").await?;

    Ok(())
}

async fn other_task(user: &mut GooseUser) -> GooseTaskResult {
    let _goose = user.get("/bar").await?;

    Ok(())
}

Optionally define a task to run before users are started and all task sets start running. This is would generally be used to set up anything required for the load test.

The GooseUser used to run the test_start tasks is not preserved and does not otherwise affect the subsequent GooseUsers that run the rest of the load test. For example, if the GooseUser logs in during test_start, subsequent GooseUser do not retain this session and are therefor not already logged in.

When running in a distributed Gaggle, this task is only run one time by the Manager.

Example
use goose::prelude::*;

#[tokio::main]
async fn main() -> Result<(), GooseError> {
    GooseAttack::initialize()?
        .test_start(task!(setup));

    Ok(())
}

async fn setup(user: &mut GooseUser) -> GooseTaskResult {
    // do stuff to set up load test ...

    Ok(())
}

Optionally define a task to run after all users have finished running all defined task sets. This would generally be used to clean up anything that was specifically set up for the load test.

When running in a distributed Gaggle, this task is only run one time by the Manager.

Example
use goose::prelude::*;

#[tokio::main]
async fn main() -> Result<(), GooseError> {
    GooseAttack::initialize()?
        .test_stop(task!(teardown));

    Ok(())
}

async fn teardown(user: &mut GooseUser) -> GooseTaskResult {
    // do stuff to tear down the load test ...

    Ok(())
}

Execute the GooseAttack load test.

Example
use goose::prelude::*;

#[tokio::main]
async fn main() -> Result<(), GooseError> {
    let _goose_metrics = GooseAttack::initialize()?
        .register_taskset(taskset!("ExampleTasks")
            .register_task(task!(example_task).set_weight(2)?)
            .register_task(task!(another_example_task).set_weight(3)?)
            // Goose must run against a host, point to localhost so test starts.
            .set_host("http://localhost")
        )
        // Exit after one second so test doesn't run forever.
        .set_default(GooseDefault::RunTime, 1)?
        .execute()
        .await?;

    Ok(())
}

async fn example_task(user: &mut GooseUser) -> GooseTaskResult {
    let _goose = user.get("/foo").await?;

    Ok(())
}

async fn another_example_task(user: &mut GooseUser) -> GooseTaskResult {
    let _goose = user.get("/bar").await?;

    Ok(())
}

Trait Implementations

Sets GooseDefault to a &str value.

Sets GooseDefault to a GooseLogFormat value.

Sets GooseDefault to a bool value.

Sets GooseDefault to a usize value.

Auto Trait Implementations

Blanket Implementations

Gets the TypeId of self. Read more

Immutably borrows from an owned value. Read more

Mutably borrows from an owned value. Read more

Convert Box<dyn Trait> (where Trait: Downcast) to Box<dyn Any>. Box<dyn Any> can then be further downcast into Box<ConcreteType> where ConcreteType implements Trait. Read more

Convert Rc<Trait> (where Trait: Downcast) to Rc<Any>. Rc<Any> can then be further downcast into Rc<ConcreteType> where ConcreteType implements Trait. Read more

Convert &Trait (where Trait: Downcast) to &Any. This is needed since Rust cannot generate &Any’s vtable from &Trait’s. Read more

Convert &mut Trait (where Trait: Downcast) to &Any. This is needed since Rust cannot generate &mut Any’s vtable from &mut Trait’s. Read more

Convert Arc<Trait> (where Trait: Downcast) to Arc<Any>. Arc<Any> can then be further downcast into Arc<ConcreteType> where ConcreteType implements Trait. Read more

Performs the conversion.

Instruments this type with the provided Span, returning an Instrumented wrapper. Read more

Instruments this type with the current Span, returning an Instrumented wrapper. Read more

Performs the conversion.

Should always be Self

The type returned in the event of a conversion error.

Performs the conversion.

The type returned in the event of a conversion error.

Performs the conversion.

Attaches the provided Subscriber to this type, returning a WithDispatch wrapper. Read more

Attaches the current default Subscriber to this type, returning a WithDispatch wrapper. Read more