i have created one feature file that contains 2 scenarios and create a step defination for that feature file but while trying to run it it openes multiple browsers i need it to open one browser.
Feature: Login
Background:
Given user navigated to SauceLap website
@Login
Scenario: user lgin with locked user
When user enter the locked userName "locked_out_user"
And user enter the password "secret_sauce"
And click on login button
Then An error message must be appears
@Login
Scenario: user login with valid credentials
When user enter a valid userName "standard_user"
And user enter a valid password "secret_sauce"
And user click on login button
Then automatically navigated to homePage
Step definitions:
namespace SpecFlowProject2.StepDefinitions
{
[Binding]
public sealed class Login
{
private IWebDriver driver;
public Login(IWebDriver driver)
{
this.driver = driver;
}
[Given(@"user navigated to SauceLap website")]
public void GivenUserNavigatedToSauceLapWebsite()
{
driver.Url = "https://www.saucedemo.com/v1/";
}
[When(@"user enter the locked userName ""([^""]*)""")]
public void WhenUserEnterTheLockedUserName(string userName)
{
driver.FindElement(By.XPath("//input[@id='user-name']")).SendKeys(userName);
}
[When(@"user enter the password ""([^""]*)""")]
public void WhenUserEnterThePassword(string Password)
{
driver.FindElement(By.Id("password")).SendKeys(Password);
}
[When(@"click on login button")]
public void WhenClickOnLoginButton()
{
driver.FindElement(By.Id("login-button")).Click();
}
[Then(@"An error message must be appears")]
public void ThenAnErrorMessageMustBeAppears()
{
Thread.Sleep(3000);
}
[When(@"user enter a valid userName ""([^""]*)""")]
public void WhenUserEnterAValidUserName(string userName)
{
driver.FindElement(By.XPath("//input[@id='user-name']")).SendKeys(userName);
}
[When(@"user enter a valid password ""([^""]*)""")]
public void WhenUserEnterAValidPassword(string Password)
{
driver.FindElement(By.Id("password")).SendKeys(Password);
}
[When(@"user click on login button")]
public void WhenUserClickOnLoginButton()
{
driver.FindElement(By.Id("login-button")).Click();
}
[Then(@"automatically navigated to homePage")]
public void ThenAutomaticallyNavigatedToHomePage()
{
Thread.Sleep(3000);
}
}
}
Hooks:
namespace SpecFlowProject2.Hook
{
[Binding]
public sealed class Hooks1
{
private readonly IObjectContainer _container;
public Hooks1(IObjectContainer container)
{
_container = container;
}
[BeforeScenario("@tag1")]
public void BeforeScenarioWithTag()
{
// Example of filtering hooks using tags. (in this case, this 'before scenario' hook will execute if the feature/scenario contains the tag '@tag1')
// See https://docs.specflow.org/projects/specflow/en/latest/Bindings/Hooks.html?highlight=hooks#tag-scoping
//TODO: implement logic that has to run before executing each scenario
}
[BeforeFeature(Order = 1)]
public void FirstBeforeScenario()
{
IWebDriver driver=new ChromeDriver();
driver.Manage().Window.Maximize();
_container.RegisterInstanceAs<IWebDriver>(driver);
}
[AfterScenario]
public void AfterScenario()
{
//TODO: implement logic that has to run after executing each scenario
}
}
}
The dependency injection container will not dispose of objects by default. The browser windows keep opening, because the web driver is created, but never destroyed. You can fix this with one of two solutions:
Explicitly dispose of the object in an
[AfterScenario]hook:Tell the DI container to dispose of the web driver automatically when registering it in a
[BeforeScenario]hook:The advantage of option 1 is you make disposing of the web driver explicit, so you can control precisely how the object is disposed of. I've had problems in the past where the driver had problems quitting and exiting memory, so I resorted to killing it by process Id, which requires some custom handling.
The advantage of option 2 is its simplicity. Tell the DI container to dispose of it, and the driver will be disposed of when the object container is disposed of. From the behavior I've observed in SpecFlow, the DI container is disposed of at the end of each scenario.
Reference: IObjectContainer.RegisterInstanceAs(...).