Skip to content
Open
Show file tree
Hide file tree
Changes from 6 commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
4 changes: 4 additions & 0 deletions .github/workflows/cicd.yml
Original file line number Diff line number Diff line change
Expand Up @@ -4,6 +4,7 @@ on:
pull_request:
paths:
- 'GitVersion.yml'
- '!mkdocs.yml'
- 'src/**'
- '!src/qodana.yml'
- '.github/actions/**'
Expand All @@ -13,12 +14,14 @@ on:
- '!.github/workflows/qodana.yml'
- '!.github/workflows/semgrep.yml'
- '!.github/workflows/snyk.yml'
- '!.github/workflows/docs.yml'
types: [opened, synchronize, reopened]
push:
branches:
- 'master'
paths:
- 'GitVersion.yml'
- '!mkdocs.yml'
- 'src/**'
- '!src/qodana.yml'
- '.github/actions/**'
Expand All @@ -28,6 +31,7 @@ on:
- '!.github/workflows/qodana.yml'
- '!.github/workflows/semgrep.yml'
- '!.github/workflows/snyk.yml'
- '!.github/workflows/docs.yml'
workflow_dispatch:
inputs:
buildAutoFakeItEasy:
Expand Down
77 changes: 77 additions & 0 deletions .github/workflows/docs.yml
Original file line number Diff line number Diff line change
@@ -0,0 +1,77 @@
name: Build Documentation

on:
push:
branches: [ master ]
paths:
- 'docs/**'
- 'mkdocs.yml'
- '.github/workflows/docs.yml'
pull_request:
branches: [ master ]
paths:
- 'docs/**'
- 'mkdocs.yml'
- '.github/workflows/docs.yml'
workflow_dispatch:

defaults:
run:
shell: pwsh

concurrency:
group: ${{ github.workflow }}-${{ github.ref }}
cancel-in-progress: true

jobs:
build:
runs-on: ubuntu-latest
timeout-minutes: 10
permissions:
contents: read
pages: write
id-token: write
steps:
- name: 📥 checkout
uses: actions/checkout@v4
with:
fetch-depth: 0

- name: 🐍 setup python
uses: actions/setup-python@v5
with:
python-version: '3.11'

- name: 📦 install mkdocs and material theme
run: |
$ErrorActionPreference = 'stop'
pip install mkdocs-material
if ($LastExitCode -ne 0) {
throw "pip install failed with exit code $LastExitCode"
}

- name: 🏗️ build documentation
run: |
$ErrorActionPreference = 'stop'
mkdocs build
if ($LastExitCode -ne 0) {
throw "mkdocs build failed with exit code $LastExitCode"
}

- name: 📤 upload pages artifact
id: artifacts
uses: actions/upload-pages-artifact@v3
with:
path: ./site

deploy:
environment:
name: github-pages
url: ${{ steps.artifacts.outputs.page_url }}
runs-on: ubuntu-latest
Comment on lines +68 to +71
Copy link

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

⚠️ Potential issue

environment.url points to a non-existent output – workflow will fail

actions/upload-pages-artifact (step artifacts) doesn’t expose a page_url output.
The page_url comes from actions/deploy-pages, which you already invoke in the step with id deployment. Reference that step instead:

-  url: ${{ steps.artifacts.outputs.page_url }}
+  url: ${{ steps.deployment.outputs.page_url }}

Without this change actionlint (and the runtime run) will error out with “property … is not defined”.

📝 Committable suggestion

‼️ IMPORTANT
Carefully review the code before committing. Ensure that it accurately replaces the highlighted code, contains no missing lines, and has no issues with indentation. Thoroughly test & benchmark the code to ensure it meets the requirements.

Suggested change
environment:
name: github-pages
url: ${{ steps.artifacts.outputs.page_url }}
runs-on: ubuntu-latest
environment:
name: github-pages
url: ${{ steps.deployment.outputs.page_url }}
runs-on: ubuntu-latest
🧰 Tools
🪛 actionlint (1.7.7)

70-70: property "artifacts" is not defined in object type {deployment: {conclusion: string; outcome: string; outputs: {page_url: string}}}

(expression)

🤖 Prompt for AI Agents
In .github/workflows/docs.yml around lines 68 to 71, the environment.url is
incorrectly set to use an output named page_url from the step with id artifacts,
which does not exist. To fix this, change the reference to use the output
page_url from the step with id deployment, which is the correct source of this
output. This will prevent actionlint and runtime errors about undefined
properties.

needs: [build]
if: ${{ github.ref_name == 'master' && needs.build.result == 'success' }}
steps:
- name: 📤 Deploy to GitHub Pages
id: deployment
uses: actions/deploy-pages@v4
2 changes: 1 addition & 1 deletion README.md
Original file line number Diff line number Diff line change
Expand Up @@ -2,7 +2,7 @@

[![CI/CD](https://img.shields.io/github/actions/workflow/status/Accenture/AutoFixture.XUnit2.AutoMock/cicd.yml?logo=githubactions&logoColor=white&label=ci%2Fcd)](https://github.com/Accenture/AutoFixture.XUnit2.AutoMock/actions/workflows/cicd.yml) [![codecov](https://codecov.io/gh/Accenture/AutoFixture.XUnit2.AutoMock/branch/master/graph/badge.svg)](https://codecov.io/gh/Accenture/AutoFixture.XUnit2.AutoMock) [![Mutation testing](https://img.shields.io/endpoint?style=flat&label=stryker&logo=stryker&url=https%3A%2F%2Fbadge-api.stryker-mutator.io%2Fgithub.com%2FAccenture%2FAutoFixture.XUnit2.AutoMock%2Fmaster)](https://dashboard.stryker-mutator.io/reports/github.com/Accenture/AutoFixture.XUnit2.AutoMock/master) [![qodana](https://img.shields.io/github/actions/workflow/status/Accenture/AutoFixture.XUnit2.AutoMock/qodana.yml?style=flat&logo=resharper&label=qodana)](https://github.com/Accenture/AutoFixture.XUnit2.AutoMock/actions/workflows/qodana.yml) [![License: MIT](https://img.shields.io/github/license/Accenture/AutoFixture.XUnit2.AutoMock?label=license&color=brightgreen)](https://opensource.org/licenses/MIT) [![fossa](https://app.fossa.com/api/projects/git%2Bgithub.com%2FObjectivityLtd%2FAutoFixture.XUnit2.AutoMock.svg?type=shield)](https://app.fossa.com/projects/git%2Bgithub.com%2FObjectivityLtd%2FAutoFixture.XUnit2.AutoMock?ref=badge_shield)

Accelerates preparation of mocked structures for unit tests under [XUnit2](http://xunit.github.io/) by configuring [AutoFixture](https://github.com/AutoFixture/AutoFixture) data generation to use a mocking library of your choice. Gracefully handles recursive structures by omitting recursions.
Accelerates preparation of mocked structures for unit tests under [XUnit2](http://xunit.net/) by configuring [AutoFixture](https://github.com/AutoFixture/AutoFixture) data generation to use a mocking library of your choice. Gracefully handles recursive structures by omitting recursions.

It provides the following mocking attributes:

Expand Down
30 changes: 30 additions & 0 deletions docs/attributes/auto-mock-data-attribute.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,30 @@
# AutoMockData Attribute

Provides auto-generated data specimens generated by [AutoFixture](https://github.com/AutoFixture/AutoFixture) with a mocking library as an extension to xUnit.net's `Theory` attribute.

## Arguments

- `IgnoreVirtualMembers` - disables generation of members marked as `virtual` (default: `false`)

## Example

```csharp
[Theory]
[AutoMockData]
public void GivenCurrencyConverter_WhenConvertToPln_ThenMustReturnCorrectConvertedAmount(
string testCurrencySymbol,
[Frozen] ICurrencyExchangeProvider currencyProvider,
CurrencyConverter currencyConverter)
{
// Arrange
Mock.Get(currencyProvider)
.Setup(cp => cp.GetCurrencyExchangeRate(testCurrencySymbol))
.Returns(100M);

// Act
decimal result = currencyConverter.ConvertToPln(testCurrencySymbol, 100M);

// Assert
Assert.Equal(10000M, result);
}
```
44 changes: 44 additions & 0 deletions docs/attributes/customize-with-attribute.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,44 @@
# CustomizeWith Attribute

An attribute that can be applied to parameters in an `AutoDataAttribute`-driven `Theory` to apply additional customization when the `IFixture` creates an instance of that type.

## Arguments

- `IncludeParameterType` - indicates whether attribute target parameter `Type` should be included as a first argument when creating customization; by default set to `false`

**Caution:** Order is important! Applying `CustomizeWith` attribute to the subsequent parameter makes preceding parameters of the same type to be created without specified customization and the particular parameter with the specified customization.

## Example

```csharp
public class LocalDatesCustomization : ICustomization
{
public void Customize(IFixture fixture)
{
fixture.Register(() => LocalDate.FromDateTime(fixture.Create<DateTime>()));
}
}
```

```csharp
[Theory]
[InlineAutoMockData("USD")]
[InlineAutoMockData("EUR")]
public void GivenCurrencyConverter_WhenConvertToPlnAtParticularDay_ThenMustReturnCorrectConvertedAmount(
string testCurrencySymbol,
[CustomizeWith(typeof(LocalDatesCustomization))] LocalDate day,
[Frozen] ICurrencyExchangeProvider currencyProvider,
CurrencyConverter currencyConverter)
{
// Arrange
Mock.Get(currencyProvider)
.Setup(cp => cp.GetCurrencyExchangeRate(testCurrencySymbol, day))
.Returns(100M);

// Act
decimal result = currencyConverter.ConvertToPln(testCurrencySymbol, 100M, day);

// Assert
Assert.Equal(10000M, result);
}
```
53 changes: 53 additions & 0 deletions docs/attributes/customize-with-t-attribute.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,53 @@
# CustomizeWith\<T> Attribute

A generic version of the `CustomizeWith` attribute has been introduced for ease of use. The same rules apply as for the non-generic version.

## Example

```csharp
public class EmptyCollectionCustomization : ICustomization
{
public EmptyCollectionCustomization(Type reflectedType)
{
this.ReflectedType = reflectedType;
}

public Type ReflectedType { get; }

public void Customize(IFixture fixture)
{
var emptyArray = Array.CreateInstance(this.ReflectedType.GenericTypeArguments.Single(), 0);

fixture.Customizations.Add(
new FilteringSpecimenBuilder(
new FixedBuilder(emptyArray),
new ExactTypeSpecification(this.ReflectedType)));
}
}
```

```csharp
public sealed class EmptyCollectionAttribute : CustomizeWithAttribute<EmptyCollectionCustomization>
{
public EmptyCollectionAttribute()
{
this.IncludeParameterType = true;
}
}
```

```csharp
[Theory]
[AutoData]
public void CustomizeWithAttributeUsage(
IList<string> firstStore,
[EmptyCollection] IList<string> secondStore,
IList<string> thirdStore,
IList<int?> fourthStore)
{
Assert.NotEmpty(firstStore);
Assert.Empty(secondStore);
Assert.Empty(thirdStore);
Assert.NotEmpty(fourthStore);
}
```
13 changes: 13 additions & 0 deletions docs/attributes/except-attribute.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,13 @@
# Except Attribute

Ensures that values from outside the specified list will be generated.

```csharp
[Theory]
[AutoData]
public void ExceptAttributeUsage(
[Except(DayOfWeek.Saturday, DayOfWeek.Sunday)] DayOfWeek workday)
{
Assert.True(workday is >= DayOfWeek.Monday and <= DayOfWeek.Friday);
}
```
36 changes: 36 additions & 0 deletions docs/attributes/ignore-virtual-members-attribute.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,36 @@
# IgnoreVirtualMembers Attribute

An attribute that can be applied to parameters in an `AutoDataAttribute`-driven `Theory` to indicate that the parameter value should not have `virtual` properties populated when the `IFixture` creates an instance of that type.

This attribute allows disabling the generation of members marked as `virtual` on a decorated type, whereas `IgnoreVirtualMembers` arguments of mocking attributes mentioned above disable such a generation for all types created by `IFixture`.

**Caution:** Order is important! Applying `IgnoreVirtualMembers` attribute to the subsequent parameter makes preceding parameters of the same type to have `virtual` properties populated and the particular parameter with the following ones of the same type to have `virtual` properties unpopulated.

## Example

```csharp
public class User
{
public string Name { get; set; }
public virtual Address Address { get; set; }
}
```

```csharp
[Theory]
[AutoData]
public void IgnoreVirtualMembersUsage(
User firstUser,
[IgnoreVirtualMembers] User secondUser,
User thirdUser)
{
Assert.NotNull(firstUser.Name);
Assert.NotNull(firstUser.Address);

Assert.NotNull(secondUser.Name);
Assert.Null(secondUser.Address);

Assert.NotNull(thirdUser.Name);
Assert.Null(thirdUser.Address);
}
```
22 changes: 22 additions & 0 deletions docs/attributes/index.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,22 @@
# Attributes Overview

This section describes the main attributes provided by AutoFixture.XUnit2.AutoMock for use in your xUnit tests:

## Test Method Attributes

- [AutoMockData](auto-mock-data-attribute.md): Provides auto-generated data specimens using AutoFixture and a mocking library.
- [InlineAutoMockData](inline-auto-mock-data-attribute.md): Combines inline values with auto-generated data specimens.
- [MemberAutoMockData](member-auto-mock-data-attribute.md): Uses static members as data sources, combined with auto-generated data.

## Parameter Configuration Attributes

- [IgnoreVirtualMembers](ignore-virtual-members-attribute.md): Disables generation of virtual members for a parameter or globally.
- [CustomizeWith](customize-with-attribute.md): Applies additional customization to a parameter.
- [CustomizeWith\<T>](customize-with-t-attribute.md): Generic version of CustomizeWith for ease of use.

## Data Filtering Attributes

- [Except](except-attribute.md): Ensures values from outside the specified list will be generated.
- [PickFromRange](pick-from-range-attribute.md): Ensures only values from a specified range will be generated.
- [PickNegative](pick-negative-attribute.md): Ensures only negative values will be generated.
- [PickFromValues](pick-from-values-attribute.md): Ensures only values from the specified list will be generated.
34 changes: 34 additions & 0 deletions docs/attributes/inline-auto-mock-data-attribute.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,34 @@
# InlineAutoMockData Attribute

Provides a data source for a `Theory`, with the data coming from inline values combined with auto-generated data specimens generated by [AutoFixture](https://github.com/AutoFixture/AutoFixture) with a mocking library.

## Arguments

- `IgnoreVirtualMembers` - disables generation of members marked as `virtual` (default: `false`)

## Example

```csharp
[Theory]
[InlineAutoMockData("USD", 3, 10, 30)]
[InlineAutoMockData("EUR", 4, 20, 80)]
public void GivenCurrencyConverter_WhenConvertToPln_ThenMustReturnCorrectConvertedAmount(
string testCurrencySymbol,
decimal exchangeRate,
decimal currencyAmount,
decimal expectedPlnAmount,
[Frozen] ICurrencyExchangeProvider currencyProvider,
CurrencyConverter currencyConverter)
{
// Arrange
Mock.Get(currencyProvider)
.Setup(cp => cp.GetCurrencyExchangeRate(testCurrencySymbol))
.Returns(exchangeRate);

// Act
decimal result = currencyConverter.ConvertToPln(testCurrencySymbol, currencyAmount);

// Assert
Assert.Equal(expectedPlnAmount, result);
}
```
Loading