Running Specrun and using 'Baseclass.contrib.Specflow' for cross browser parameterized tests in VS2015 - specrun

I would like to use SpecRunner along with the library 'Baseclass.Contrib.SpecFlow.Selenium.NUnit.' When I added SpecRunner for SpecFlow 2 from Manage Nuget Packages, the unit test provider was 'SpecRun' in app.config. Then when added to 'Baseclass.Contrib.SpecFlow.Selenium.NUnit' to the solution using Manage Nuget Package, it also added a unit test provider of 'SeleniumNUnit. When I created my feature files and step definitions and tried to run the tests with each feature annotated with a browser tag like '#Browser: Chrome' and use the 'Browser.Current' syntax as the webdriver in my binding methods, it gave me an error. The error was first that I had two unit test providers in the app.config, and that the app.config can only have one unit test provider. SO I commented out the first unit test provider, and received another set of errors:
*Error 2 #error: 'Generation error: Could not load file or assembly 'TechTalk.SpecFlow, Version=1.9.0.77, Culture=neutral, PublicKeyToken=0778194805d6db41' or one of its dependencies. The system cannot find the file specified.' C:\Users\amaddox\documents\visual studio 2013\Projects\SpecFlow\SpecFlow\SpecFlowFeature1.feature.cs 1 8 SpecFlow
*
*Error 33 Custom tool error: Generation error: Could not load file or assembly 'TechTalk.SpecFlow, Version=1.9.0.77, Culture=neutral, PublicKeyToken=0778194805d6db41' or one of its dependencies. The system cannot find the file specified. C:\Users\amaddox\documents\visual studio 2013\Projects\SpecFlow\SpecFlow\SpecFlowFeature1.feature 2 2 SpecFlow
*
So then I tried to uncomment the first and comment the second unit test provider. Same issue. How can I run SpecRun in visual Studio 2015 along with the flexibility of parameterized cross browser tests functionality that 'Baseclass.Contrib.SpecFlow.Selenium.NUnit.Bindings' has to offer? It appears that it wants me to go back to a previous version of Specflow (1.9) and I am using Specflow 2. Not sure how to do this. How do I solve this issue?
<?xml version="1.0" encoding="utf-8"?>
<configuration>
<configSections>
<section name="specFlow" type="TechTalk.SpecFlow.Configuration.ConfigurationSectionHandler, TechTalk.SpecFlow" />
<section name="autofac" type="Autofac.Configuration.SectionHandler, Autofac.Configuration" /></configSections>
<specFlow>
<!-- For additional details on SpecFlow configuration options see http://go.specflow.org/doc-config -->
<!-- For additional details on SpecFlow configuration options see http://go.specflow.org/doc-config --><!-- use unit test provider SpecRun+NUnit or SpecRun+MsTest for being able to execute the tests with SpecRun and another provider --><unitTestProvider name="SpecRun" /><plugins>
<add name="SpecRun" />
<add name="Baseclass.Contrib.SpecFlow.Selenium.NUnit" path="..\packages\Baseclass.Contrib.SpecFlow.Selenium.NUnit.1.3.1\tools" /></plugins><unitTestProvider name="SeleniumNUnit" /><stepAssemblies>
<stepAssembly assembly="Baseclass.Contrib.SpecFlow.Selenium.NUnit.Bindings" />
</stepAssemblies></specFlow>
<appSettings>
<add key="seleniumBaseUrl" value="http://localhost:58909" />
</appSettings><autofac>
<components>
<component name="IE" type="OpenQA.Selenium.IE.InternetExplorerDriver, WebDriver" service="OpenQA.Selenium.IWebDriver, WebDriver" instance-scope="per-dependency">
</component>
<component name="Chrome" type="OpenQA.Selenium.Chrome.ChromeDriver, WebDriver" service="OpenQA.Selenium.IWebDriver, WebDriver" instance-scope="per-dependency">
</component>
<component name="Firefox" type="OpenQA.Selenium.Firefox.FirefoxDriver, WebDriver" service="OpenQA.Selenium.IWebDriver, WebDriver" instance-scope="per-dependency">
</component>
<!-- Example of using an injected RemoteDriver:
<component
name="IE"
type="Baseclass.Contrib.SpecFlow.Selenium.NUnit.RemoteWebDriver, Baseclass.Contrib.SpecFlow.Selenium.NUnit.SpecFlowPlugin"
service="OpenQA.Selenium.IWebDriver, WebDriver"
instance-scope="per-dependency">
<parameters>
<parameter name="url" value="http://127.0.0.1:4444/wd/hub" />
<parameter name="browser" value="InternetExplorer">
</parameter>
</parameters>
</component>-->
</components>
</autofac>
<runtime>
<assemblyBinding xmlns="urn:schemas-microsoft-com:asm.v1">
<dependentAssembly>
<assemblyIdentity name="TechTalk.SpecFlow" publicKeyToken="0778194805d6db41" culture="neutral" />
<bindingRedirect oldVersion="0.0.0.0-2.1.0.0" newVersion="2.1.0.0" />
</dependentAssembly>
</assemblyBinding>
</runtime>
</configuration>
*

After a short look at Baseclass.Contrib.SpecFlow.Selenium.NUnit it depends on SpecFlow 1.9. If you want to use it, you have to stick on SpecFlow 1.9.
Additionally it looks like they create their own GeneratorPlugin to generate custom code behind files.
That does not work together with SpecFlow+Runner as it has its own generator.
And two unitTestProviders in the config does not work.
But the SpecFlow+Runner has a feature called "Targets" see http://www.specflow.org/plus/documentation/SpecFlowPlus-Runner-Profiles and search for it there.
You can create a target for each of your browsers and use the ConfigFileTransformation Step to adjust your config for your different browsers.
Another way, but I am not sure if this work. SpecFlow+Runner has support for SpecFlow 1.9 and can execute NUnit tests.
Use the SpecRun.SpecFlow.1-9-0 nuget package and configure the unitTestProvider to the one of baseClass. If they generate the standard NUnit attributes, the SpecFlow+Runner should find the tests and can execute them. But be aware, that you are losing some features with that method.
Full disclosure: I am one of the developers of SpecFlow and SpecFlow+

I rewrote Baseclass.Contrib.SpecFlow.Selenium.NUnit for 2.1 support.
New codebase, #ignore tag support for nunit3 and several testing services like BrowserStack, SauceLabs, TestingBot.

Related

Compile application twice with different manifest files

Is there a way to compile a WPF application twice in Visual Studio (version 2015/2017) with different manifest files?
On the one hand I need the application to require administrator permissions, on the other hand the same application without administrator permissions (means: without or another manifest file).
With compile constants I'm able to do something like this:
<?xml version="1.0" encoding="utf-8"?>
<assembly manifestVersion="1.0" xmlns="urn:schemas-microsoft-com:asm.v1">
<assemblyIdentity version="1.0.0.0" name="Update.app"/>
<trustInfo xmlns="urn:schemas-microsoft-com:asm.v2">
<security>
<requestedPrivileges xmlns="urn:schemas-microsoft-com:asm.v3">
#if ADMIN
<requestedExecutionLevel level="requireAdministrator" uiAccess="false" />
#endif
</requestedPrivileges>
</security>
</trustInfo>
</assembly>
but this doesn't seem to work like expected.
A solution where I only need to click the build button once and receive two applications would be perfect.
Another possible solution is to use post-build commands, but I'm not sure if this will work.
There is an option in Visual Studio 2017 (and maybe earlier versions, I cannot confirm) that allows you to build multiple configurations in a single run.
Look at the toolbar menu: "Build" > "Batch Build"

Loading NUnit project file (example.nunit) during Specflow feature execution

To enable environment configuration, I included an NUnit project as part of the SpecFlow BDD framework (as per Pass parameters via command line to NUnit). But when I try to load it from the command prompt, I am getting the error message
.\nunit-console-x86.exe : Unable to locate fixture.
Command trying to run:
nunit-console-x86.exe example.nunit /config:CI /run:"xxxx.Features.abcdFeature" $dll_dir /result=$result_dir
The framework is as per SpecFlow and Selenium-Share data between different step definitions or classes,
using NUnit 2.6.4 and SpecFlow 1.9.
My NUnit project file. Do we need to pass a .csproj file or DLL file in the nunit.exe command above?
<NUnitProject>
<Settings activeconfig="Default" />
<Config name="Default" configfile="App.CI.config">
<assembly path="C:\FuncTest\{ProjectName}\{ProjectName}\bin\Debug\{ProjectName}.dll" />
</Config>
<Config name="CI" configfile="App.CI.config">
<assembly path="C:\FuncTest\{ProjectName}\{ProjectName}\bin\Debug\{ProjectName}.dll" />
</Config>
<Config name="UAT" configfile="App.UAT.config">
<assembly path="C:\FuncTest\{ProjectName}\{ProjectName}\bin\Debug\{ProjectName}.dll" />
</Config>
</NUnitProject>
I assume that you have a project containing at least one test fixture which looks something like this:
[TestFixture]
public class MyFirstTestFixture{
[Test]
public void MyFirstTest(){
..
}
}
So if you project is called myfirstproj.csproj, which contains this fixture, this will produce the following file myfirstproj/bin/debug/myfirstproj.dll.
Note you can replace debug with release, if you compiled it with the release setting. I assume we use debug for now.
Now you create a new NUnit file (in the same folder as the myfirstproj.csproj) file and place the contents like this (I assume you call it myfirstproj.nunit):
<NUnitProject>
<Settings activeconfig="local"/>
<Config name="local" configfile="App.config">
<assembly path="bin\Debug\myfirstproj.dll"/>
</Config>
</NUnitProject>
Now when you want NUnit you do it like this:
nunit3-console.exe myfirstproj.nunit /config:local
So for the difference between your setup and mine:
Specify the relative path of the DLL file from the NUnit file
Specify that path without placeholders
Execute the test, using the NUnit file
Does this work for you?
If you want to debug this, I would use this steps:
Create first an empty project with just a single unit test
Run that test by executing nunit3-console.exe c:\absolutepath\to\my\project.dll
If the above works, start creating the NUnit file and run it using the NUnit file and see if that works.
Try specifying a configuration and using that configuration for the different environments.

Could not load file or assembly Microsoft.Data.OData Version=5.2.0.0 error in Azure Cloud Worker Role using Table Storage

I have a very peculiar issue using Azure Table Storage. I have a .NET 4.5 project in Visual Studio 2012 where I deal with all my Azure Table Storage functions. This project/dll is referenced by two other projects, my MVC website, and my Azure Worker Role. (I am running under the Azure Emulators on my machine, but it also happens when I deploy it to the cloud)
I have the following function that is called when I save or retrieve a record:
internal static CloudTable GetTable(CloudStorageAccount storageAccount, string tableReference)
{
CloudTableClient tableClient = storageAccount.CreateCloudTableClient();
CloudTable table = tableClient.GetTableReference(tableReference);
table.CreateIfNotExists();
return tableClient.GetTableReference(table.Name);
}
In my MVC website I have a function that will save a record to a Azure Storage table, and then in my Azure Worker Role there is a service that will read the record.
So both uses the same dll for storage and retrieval, however my MVC project has no issues saving the record, but in my Azure Worker role service when it tries to retrieve the record throws the exception when it attempts to execute "table.CreateIfNotExists();".
Could not load file or assembly 'Microsoft.Data.OData,
Version=5.2.0.0, Culture=neutral, PublicKeyToken=31bf3856ad364e35' or
one of its dependencies. The located assembly's manifest definition
does not match the assembly reference. (Exception from HRESULT:
0x80131040)
I have done the following already:
Updated all the NuGet packages from the solution level to the latest versions
I went through every project reference to make sure that there are no old dll's or previous versions hanging around, in particular the System.Spatial, Microsoft.WindowsAzure.Configuration, Microsoft.WindowsAzure.ServiceRuntime and Microsoft.ServiceBus, Microsoft.WindowsAzure.Storage, Microsoft.Data.Edm & Microsoft.Data.OData
I have even created a new Cloud Service and WorkerRole project from scratch to make sure it is not something in the current WorkerRole project that is broken.
I have not rolled the dll's back to 5.2 as I had too many issues in other projects where I use features that are specific from 5.3 onwards.
I am currently running all the dll's on 5.5.
When I run the AsmSpy.exe utility found here, I get the following output that I am not 100% sure how to interpret.
> Reference: Microsoft.Data.Edm
> 5.5.0.0 by Microsoft.Data.OData
> 5.5.0.0 by Microsoft.Data.Services.Client
> 5.5.0.0 by Microsoft.WindowsAzure.ActiveDirectory.GraphHelper.2013_04_05
> Reference: System.Spatial
> 5.5.0.0 by Microsoft.Data.OData
> 5.5.0.0 by Microsoft.Data.Services.Client Reference: Microsoft.Data.OData
> 5.5.0.0 by Microsoft.Data.Services.Client
> 5.2.0.0 by Microsoft.WindowsAzure.Storage <-- THIS SEEMS TO BE THE ONE THAT IS CAUSING ISSUES
How I interpret it, is that the Microsoft.WindowsAzure.Storage dll is referencing V 5.2.0.0 of the Microsoft.Data.OData dll, but how do I fix this, if this is the issue? According to the documentation I have seen on the Storage dll is that it is supposed to reference 5.4 and up, not 5.2...?
Opening issue for such an easy to solve issue will not help you.
Put the following addition configuration in your respective config files (web.config for the MVC and app.config for the worker role):
<runtime>
<assemblyBinding xmlns="urn:schemas-microsoft-com:asm.v1">
<dependentAssembly>
<assemblyIdentity name="Microsoft.Data.OData" publicKeyToken="31bf3856ad364e35" culture="neutral" />
<bindingRedirect oldVersion="0.0.0.0-5.5.0.0" newVersion="5.5.0.0" />
</dependentAssembly>
<dependentAssembly>
<assemblyIdentity name="Microsoft.Data.Edm" publicKeyToken="31bf3856ad364e35" culture="neutral" />
<bindingRedirect oldVersion="0.0.0.0-5.5.0.0" newVersion="5.5.0.0" />
</dependentAssembly>
</assemblyBinding>
</runtime>
Note that runtime section is direct descendant of the configuration root element! I'm pretty sure you already have this section in your web.config, because MVC4 uses it to rebind all references to System.Web.MVC to the latest version.
I personally do not expect the SDK to be updated with every new version of every referenced library! This would be madness...
I had a very similar problem but in this case it exception message was;
Could not load file or assembly 'Microsoft.Data.OData,
Version=5.5.0.0, Culture=neutral, PublicKeyToken=31bf3856ad364e35' or
one of its dependencies. The located assembly's manifest definition
does not match the assembly reference. (Exception from HRESULT:
0x80131040)
note it was trying to load v5.5.0.0 of the OData assembly.
After some digging around with ILSpy (http://www.ilspy.net) I discovered that Microsoft.WindowsAzure.Storage 2.0.0.0 was explictly referencing Microsoft.Data.OData 5.2.0.0 - which I didn't have as my version was 5.5.0.0.
So the solution was to use the NuGet package manager to uninstall Microsoft.WindowsAzure.Storage, this inturn uninstalled Microsoft.Data.OData 5.5. Then again using the NuGet package manager, reinstall Microsoft.WindowsAzure.Storage which identified that it needed Microsoft.Data.OData 5.2 and installed that too.
and back to a working solution.
You can solve this issue in general whenever you update packages or add new packages via NuGet and end up with "Could Not Load file or Assembly..." issues.
Open the Package Manager Console (VS 2012 Tools/Library Package Manager/ Package Manager Console). Once the shell opens for the Package Manager Console run the command:
Add-BindingRedirect
Note: Be careful as the NugGet example added an 's' to the end in their example and Add-BindingRedirect is not a valid command.
This does the following:
Examines all assemblies in the output path for a project and adds
binding redirects to the application configuration (app.config) file
or to the web configuration (web.config) file where required.
You can see complete documentation for the Package Manager Console at: http://nuget.codeplex.com/wikipage?title=Package%20Manager%20Console%20Command%20Reference%20(v1.3)
In addition to the two entries you see in astaykov's answer the following was also added for my Project.
<dependentAssembly>
<assemblyIdentity name="System.Spatial" publicKeyToken="31bf3856ad364e35" culture="neutral" />
<bindingRedirect oldVersion="0.0.0.0-5.5.0.0" newVersion="5.5.0.0" />
</dependentAssembly>
I had similar problem today. The only difference I spotted is my cloud app was looking (and failing to find) for Microsoft.Data.OData in Version=5.2.0.0
Using Visual Studio Object Browser i found out that my solution used library from that location:
C:\Program Files (x86)\Microsoft WCF Data Services\5.0\bin\.NETFramework
Microsoft.Data.OData library residing there was in ver. 5.0.0.0 so overwriting it with 5.2.0.0 resolved the problem.
P.S. I installed WCF Data Services Tools for Windows Store Apps earlier in hope of resolving this issue so it may happen that your application gets it from another source. If that is the case you have two options:
Install WCF Data Services Tools for Windows Store Apps from here and use solution above.
Use Visual Studio Object Browser to find what versions of OData library are currently visible for your project and where they are stored. Next you need to overwrite improper versions of them.
I had a similar problem as well, but I wasn't using Azure and there was no hard-coded reference that was pointing to 5.2. But it resolved (after finding this article) by making sure that the text in the .svc pointed to the correct assembly:
<%# ServiceHost Language="C#"
Factory="System.Data.Services.DataServiceHostFactory,
Microsoft.Data.Services, Version=5.6.0.0,
Culture=neutral, PublicKeyToken=31bf3856ad364e35"
Service="MVC4WCFDataServiceFE5.NorthWindService" %>
Note the Version=5.6.0.0, which I didn't have before.

Compile AppEngine project that has datastore callbacks with Ant

I've implemented datastore callbacks in our AppEngine project and set it up in Eclipse as indicated in the link.
Now I'm having trouble getting it to compile in Ant. Here's what I have for the javac target now:
<path id="appengine.api.path">
<pathelement location="${appengine.folder}/lib/impl/appengine-api.jar" />
</path>
<target name="javac" depends="clean,libs" description="Compile java source">
<mkdir dir="war/WEB-INF/classes" />
<apt compile="false" preprocessdir=".apt_build_generated" destdir="war/WEB-INF/classes"
srcdir="src"
factorypathref="appengine.api.path"
>
</apt>
<javac srcdir="src" includes="**" encoding="utf-8" destdir="war/WEB-INF/classes" source="1.6" target="1.6" nowarn="true" debug="true" debuglevel="lines,vars,source">
<classpath refid="project.class.path" />
</javac>
<copy todir="war/WEB-INF/classes">
<fileset dir="src" excludes="**/*.java" />
</copy>
</target>
The apt task runs but all it does is list a bunch of annotations that don't have processor, including the PrePut annotation.
I've tried setting factorypathref to the ${appengine.folder}/lib/impl/appengine-api.jar but then it says the appengine-api.jar reference is not found (I've verified the path exists). I've also looked through the jar file to see if I can find the class it uses as the factory but haven't found it yet.
Finally discovered the problem. We were using the Eclipse compiler in our Ant build for other reasons. When we switched back to the built-in Java compiler, the annotation processor started working fine.

SubSonic and app.config in Windows Form

As it should be the file app.config in an application Windows Form so that the given access classes her they generate automatically in the build?
Yes. What you do is add a section in configSections called "SubsonicService", like this:
<configSections>
<section name="SubSonicService" type="SubSonic.SubSonicSection, SubSonic" requirePermission="false"/>
</configSections>
Next, you add a connectionStrings branch with the connection strings that you will use in your project, like this:
<connectionStrings>
<clear/>
<add name="WheelMUDSQLite" connectionString="Data Source=C:\Dev\WheelMud.net\src\SQL\SQLite\WheelMud.net.db;Version=3;"/>
</connectionStrings>
Last, you add the SubsonicService node that you added in the configSections like this:
<SubSonicService defaultProvider="WheelMUDSQLite">
<providers>
<clear/>
<add name="WheelMUDSQLite" type="SubSonic.SQLiteDataProvider, SubSonic" connectionStringName="WheelMUDSQLite" generatedNamespace="WheelMUD.DataLayer"/>
</providers>
</SubSonicService>
This is where you put all of your providers. I use the SubStage utility to generate the DAL. This way you can completely disassociate your stuff from the Web bits that come with Subsonic.
Your build process needs to include a command like this:
sonic.exe generate /config "c:\myproject\App.config"
sonic.exe is the SubCommander utility, and is included in the current release. There's no way to have the app.config handle this for you directly.
One way to run the command is with MSBuild. The Exec MS Build task task might look something like this:
<Target Name="GenerateSubSonicClasses" DependsOn="BeforeBuild">
<Exec Command="sonic.exe generate /config "c:\myproject\App.config"" WorkingDirectory="c:\path-to-subcommander"/>
</Target>
I just made this up, so it probably needs tweaking before it'll work for you. This command would go in your visual studio project file (ie someproject.vbproj).

Resources