Thursday, April 7, 2022

Simple ASP.NET core/Angular app

 After finding several confusing articles with hit-and-miss results, I thought I would record the simplest process I have found for creating a new Angular/ASP.NET web application.

The tools I am using

  • Git: https://www.nuget.org/downloads
  • Node.js, version 16.14.0: https://nodejs.org/en/download/
  • npm, version 8.3.1 (included in the Node install)
  • VS Code, version 1.65.1: https://code.visualstudio.com/download

Getting started

Once you've got the above tools installed, open a command prompt to the root folder where you do your development (for example, c:\dev on windows).  I advise creating a parent folder (replacing [yourapplicationname]):

mkdir [yourapplicationname]

Then 

cd [yourapplicationname]

 

Then (note the -UI at the end):
dotnet new angular [yourapplicationname]-UI

 

This will generate everything you need to start working on an ASP.NET core web app with an Angular front end.  However, it will install version 8 of Angular, which is pretty old (it was released in May, 2019 and -- at the time of this article --  the current version is 13.3.1).

At this point, there are a few considerations:
  1. Do I care about using the latest versions of everything (specifically, Angular)?
  2. Am I keeping this as simple as possible, or do I want to emulate a real production application?
Question 1 above is the biggest factor in how to proceed.  I found a number of articles that described different approaches but didn't explain the pros and cons that would lead you to pick one over the other.

Quick and easy - with an old version

If you're not concerned about the latest and greatest, you can start working on the code as is.  Upgrading such an old version can be a painful process, so I recommend going with some extra steps.

Almost as quick and easy - with the newest shinies

If you prefer to go with the most up-to-date framework versions, I suggest a little more work.

Open a command prompt and navigate to the web app folder you created before
cd c:\dev\[yourapplicationname]\[yourprojectname]-UI

Remove the Angular code created by dotnet:

rmdir ClientApp

Create a new Angular client app:

ng new ClientApp

You will be prompted to add Angular routing.  Type "y" to accept.

 You will be prompted for a stylesheet format.  Just hit enter to accept the pre-selected CSS.

Testing the base application

Open VS Code and select File > Open Folder and select the root folder of your application (C:\Dev\[yourapplicationname]).

Select Terminal > New Terminal.

In the terminal, navigate to the web application folder and start the application:
      cd [yourapplicationname]-UI       dotnet run

At the time of this article's publication, you may see some false error messages from Microsoft.AspNetCore.SpaServices[0] like

Generating browser application bundles (phase: setup)... or

 Γ£ö Browser application bundle generation complete.

These are due to the dotnet CLI misinterpreting progress output from Angular (see https://github.com/dotnet/aspnetcore/issues/21793).  There seems to be a stalemate currently on which team is going to address this so -- if it bothers you -- you can turn off Angular output by opening angular.json and adding "progress": false,

      "architect": {
        "build": {
          "builder": "@angular-devkit/build-angular:browser",
          "options": {
            "progress": false,
            "outputPath": "dist/client-app",

Once the app is running, you can open a browser window to https://localhost:5001/. 

 

 


Sunday, August 4, 2013

Updating FitNesse for color blind users

The importance of designing for the color blind has always been at periphery of my awareness while building applications but was recently brought to the foreground when presenting a suite of Fitnesse test results to my boss. When he asked how to determine whether a test passed or failed, I was a little puzzled by the question. I thought the red and green colors were quite obvious. That's when he had to remind me that he is color blind (most likely protanopia or a variant, as red/green seems to be particularly problematic).
Of course, I was embarrassed at neither remembering this nor coming up with a solution before having it pointed out. Nonetheless, I remembered when first getting acquainted with Fitnesse a mention of customization of the stylesheets in the user guide.
Digging around a bit, I discovered a very simple solution. I created two png files, pass.png and fail.png and placed them in c:\fitnesse\files\images. Then I modified c:\fitnesse\files\css\fitnesse.css as follows:
@import url( "/files/css/fitnesse_base.css" ); .pass { background-color: #AAFFAA; padding: 0px 0px 0px 20px; background-image: url("../images/pass.png"); background-repeat: no-repeat; } .fail { background-color: #FFAAAA; padding: 0px 0px 0px 20px; background-image: url("../images/fail.png"); background-repeat: no-repeat; zoom: 1; } #test-summary { padding: 0px 0px 0px 20px; }

Wednesday, July 27, 2011

Using FitNesse and TFS

Getting Fitnesse to work with an external source control system is not possible "out-of-the-box," though it does implement a source control provider interface that supports other providers. Thanks to Lars-Erik ?, there is a FitNesseTFS plugin available on SourceForge.

Caveats:
  1. This is an alpha product, and we've only tested it for a couple of weeks so far. Your mileage may vary.
  2. All users will be editing the same instance of fitnesse. There is no way to track who made changes to the wiki (all changes will be committed as the account under which the service runs), and there is no way to provide commit comments.

On the fitnesse server:
The first thing to do is to edit your path environment variable to include the path to TFS (for me, C:\Program Files (x86)\Microsoft Visual Studio 10.0\Common7\IDE) and Java (C:\Program Files (x86)\Java\jre6\bin).

I'll assume a Fitnesse root of c:\fitnesse.

Download the latest Fitnesse jar file.

Open a command prompt and run java -jar fitnesse.jar -p 8080 -e 0. This will run the Fitnesse unpacking process to give you a base install (and disable built-in versioning). Once it's done, close the command window.

Create a plugins folder at c:\fitnesse\plugins. Add the fitnesseTFS jar file.

You'll want Fitsharp, so download it and add the binaries to c:\fitnesse\fitsharp.

Run java -jar fitnesse.jar -p 8080 -e 0.
Run tf.exe workfold $/Infrastructure/fitnesse c:\fitnesse
Run tf.exe get c:\fitnesse /noprompt /all /overwrite /force /recursive
Run attrib *.* -R /S

Open a browser and navigate to http://localhost:8080/root

Click the edit button and enter the following:
!define TEST_SYSTEM {slim}
!define COMMAND_PATTERN {%m -r fitSharp.Slim.Service.Runner,c:\fitnesse\fitsharp\fitsharp.dll %p}
!define TEST_RUNNER {c:\fitnesse\fitsharp\Runner.exe}
!define CM_SYSTEM {fitnesseTfs.SourceControlPlugin C:\Users\me\Documents\Fitnesse\ "C:\Program Files\Microsoft Visual Studio 9.0\Common7\IDE\"}

Click the Save button, and close your browser.

Follow the instructions in this article to set up fitnesse as a service.

For developers who need to work locally,
  • get latest from TFS on the Fitnesse project
  • Run the following:

  • cd c:\fitnesse
    attrib *.* -R /S
    java -jar fitnesse.jar -p 8080 -e 0

  • Start a browser and navigate to http://localhost:8080/FrontPage

  • Click the Properties button

  • In the Remote Wiki Url text box, enter the path to the server's wiki (something like http://buildserver:8080/FrontPage).

  • Check the Automatically update imported content when executing tests checkbox, then click the Import button.


You can now work on a local version of the fitnesse wiki while you work on fixtures without impacting other users.

Thursday, June 17, 2010

Upgrading Visual Studio Projects to 2010

Just a couple of notes that may be helpful:

Certificate Issues
Problem: Build error similar to "Cannot import the following key file: [your_key_file].pfx. The key file may be password protected. To correct this, try to import the certificate again or manually install the certificate to the Strong Name CSP with the following key container name: [your_key]"

Solution: Open the Visual Studio Command Prompt, then execute the following - sn -i [your_key_file].pfx [your_key]


Target Framework Issues
Problem: Build error similar to "The referenced assembly "log4net, Version=1.2.10.0, Culture=neutral, PublicKeyToken=1b44e1d426115821, processorArchitecture=MSIL" could not be resolved because it has a dependency on "System.Web, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b03f5f7f11d50a3a" which is not in the currently targeted framework ".NETFramework,Version=v4.0,Profile=Client". Please remove references to assemblies not in the targeted framework or consider retargeting your project."

Solution: Change the target framework of the project to one of the non-client frameworks (e.g., .NET Framework 4 instead of .NET Framework 4 Client Profile).

Friday, November 13, 2009

Using NUnit with log4net

Those who know me are aware that my obsessive-compulsive nature has latched on to TDD over the past few years. While I don't slavishly pursue 100% code coverage, I'll admit that anything below 80% really starts to get me pacing and much lower than that gives me the shakes for more green bars.

One of the areas I hadn't spent much time on was logging coverage. Partly because I hadn't found a good solution and partly because the types of applications I had been working on didn't really require much in the way of logging. My latest assignment, however, is another integration framework with lots of moving parts that screams logging and lots of it, particularly as I try to refactor a legacy code base I inherited.

Thanks to articles by David Hogue and Robert Prouse, the solution is incredibly simple.

The first step is to create a custom appender. The easiest way I found was to create a class that derives from AppenderSkeleton. I had it write to a static List<string> for the sake of simplicity.

1 namespace Integrations.Framework.Tests

2 {

3 class ListAppender:log4net.Appender.AppenderSkeleton

4 {

5 public static List<string> logTable = new List<string>();

6

7 protected override void Append(log4net.Core.LoggingEvent loggingEvent)

8 {

9 logTable.Add(RenderLoggingEvent(loggingEvent));

10 }

11 }

12 }



The next step was to programatically configure log4net. Something that initially tripped me up here was that I had defined a log4net configuration in an app.config in my test project. This apparently takes precedence over programmatic configuration (or else I just had something mucked up). Anyway, my programatic configuration would not take effect until I deleted the app.config.

1 namespace Integrations.Framework.Tests

2 {

3 [TestFixture]

4 public class DataGathererTests:DataGathererBase

5 {

6 private ListAppender appender;

7 private static ILog log;

8

9 [TestFixtureSetUp]

10 public void OneTimeSetup()

11 {

12 appender = new ListAppender();

13 appender.Layout = new log4net.Layout.SimpleLayout();

14 appender.Threshold = log4net.Core.Level.Fatal;

15 log4net.Config.BasicConfigurator.Configure(appender);

16 log = LogManager.GetLogger(typeof(ListAppender));

17 }



Notice above that I've derived my test class from my base class that implements logging. I want to make sure I'm not creating an artificial layer, so I'm deriving from that base class just as I expect my "real" code to do. Now I can call any of the logging methods, setting log level appropriately and check that messages are getting logged. Once I see that simple tests like log message count are passing, I can move on to more complicated tests that examine actual log messages to make sure the text is as expected, the correct log level, etc. Also, make sure to put a logTable.Clear() call in a TearDown method to make sure tests don't interfere with one another or become dependent upon one another for system state.

19 [Test]

20 public void TestLogging()

21 {

22 this.LogDebug("Debug");

23 Assert.AreEqual(0, ListAppender.logTable.Count());

24

25

26 appender.Threshold = log4net.Core.Level.Debug;

27 this.LogDebug("Debug");

28 Assert.AreEqual(1, ListAppender.logTable.Count());

29 }

Tuesday, March 3, 2009

Slim...Fast!

For those who haven't read the blog posts or tweets, Uncle Bob has been slaving away on a new addition to Fitnesse.

In addition to Uncle Bob's intro and video, Brett Schuchert has written up an excellent article on Mike Stockdale's .NET implementation of Slim (as well as an example Slim implementation).

As with Fitnesse, Slim can be set up to run as a service.

Setting up Slim and Fitnesse

  1. Download the latest Fitnesse release.

  2. Download the latest slim release.

  3. Configure slim as the test runner.
    !*****> System-wide settings
    !define TEST_SYSTEM {slim}
    !define TEST_RUNNER {..\nslim\build\Debug\Runner.exe}
    !define COMMAND_PATTERN {%m -r fitnesse.slim.Runner,..\nslim\build\Debug\fitnesse.dll %p}
    ******!




Running Fitnesse as a service

  1. Get the Windows Resource Kit.

  2. Install the Windows 2003 Resource Kit. You will only need the instsrv.exe and srvany.exe programs. So you can copy those out and deinstall the kit if you don't want it around.

  3. Use the instsrv.exe program to install the srvany.exe program by using it like this from the command-line:

    instsrv.exe FitNesse "[path]\srvany.exe"

  4. Run the regedit.exe program to set the last parameters.

  5. Find the key HKEY_LOCAL_MACHINE\SYSTEM\CurrentControlSet\Services\FitNesse

  6. Create a subkey with the name Parameters

  7. In the parameters key, create a string value called Application and set its value to the full path of the java.exe file. For me it was:
    C:\Program Files\Java\jre6\bin\java.exe.

  8. Create another string value called AppDirectory and set its value to the path where you want the executable to run. The directory where your FitNesse files are located : c:\Program Files\FitNesse

  9. Create a last string value called AppParameters containing the parameters passed to the java executable above : -cp fitnesse.jar -Xrs fitnesse.FitNesse -p 8080

  10. Open the service control panel and start the service.


A few observations that may make your implementation smoother:


  • Although instsrv supports passing credentials, I don't advise it. On some machines, it didn't seem to set up the correct rights for the service account. Just add the account on the Log On tab of the service.

  • For errors that you may encounter, see this article


I hope you find these instructions helpful. Happy testing.

-David

Sunday, June 1, 2008

How I Learned to Stop Worrying and Love Fitnesse and .NET 2.0

*update - 2008/12/23* Most of the problems this article describes have now been resolved with the latest release of Fitnesse (which finally includes a working version of the .NET fitlibrary). Ignore the Installing Fitnesse section, but the Running Fitnesse as a Service steps still apply.

If you’re anything like me, you like to find a solution that works the first time without a lot of hassle. Unfortunately, Fitnesse with the .NET 2.0 framework was neither. Here’s a step-by-step guide to avoiding the many pitfalls along the path to test enlightenment.

Installing Fitnesse

  1. Download the 06/2007 release of Fitnesse.
  2. Unzip the archive. Note the dotnet folder will be empty.
  3. Edit the fitnesse\run.bat file to include -p 8080 if IIS is running on the same server:java -cp fitnesse.jar fitnesse.FitNesse -p 8080 %1 %2 %3 %4 %5pause
  4. Download the .NET fit library.
  5. Unzip the archive to the dotnet folder of fitnesse (e.g., c:\fitnesse\dotnet).
  6. Double-click the run.bat file (e.g., c:\fitnesse\run.bat).
    1. A command window will open with the following:>java -cp fitnesse.jar fitnesse.FitNesse -p 8080FitNesse (20070619) Started…port: 8080root page: fitnesse.wiki.FileSystemPage at ./FitNesseRootlogger: noneauthenticator: fitnesse.authentication.PromiscuousAuthenticatorhtml page factory: fitnesse.html.HtmlPageFactorypage version expiration set to 14 days.
    2. If you see something like the following, you need to install Java:‘java’ is not recognized as an internal or external command, operable program or batch file.
  7. Fire up your favorite browser, and enter http://localhost:8080/FrontPage. This will take you to the main fitnesse page.
  8. Start editing.
    1. If you want to be able to edit the main page, browse to http://localhost:8080/FrontPage?properties and select the Edit checkbox, then click the Save Properties button.
    2. Otherwise, enter a new page name (e.g., http://localhost:8080/MyNewTest). This will ask you if you want to create a new page.
  9. Whichever path you choose on the previous step, go into the edit page and enter the following:
    !***> root config
    !define COMMAND_PATTERN {%m %p}
    !define TEST_RUNNER {dotnet\FitServer.exe}
    !define PATH_SEPARATOR {;}
    ***!
  10. Make sure your fixture projects reference fit and FitLibrary (though you’ll refer to FitLibrary as fitlibrary in code) in the fitness\dotnet folder if you want to use DoFixtures.
    Make sure you set the Fit reference to copy local=false. This will prevent hours of lost productivity trying to figure out what the heck "Couldn't cast YourFixtureNameHere to Fixture. Did you remember to extend Fixture" errors mean.
  11. Edit each test page (alternatively, you can just add this to a root page — it will be inherited by all child pages) with:
    !path path_to_your_test_fixture_dll

That’s it! You’re on your way to creating tests with Fitnesse and the 2.0 framework.

Running Fitnesse as a service

  1. Get the Windows Resource Kit.

  2. Install the Windows 2003 Resource Kit. You will only need the instsrv.exe and srvany.exe programs. So you can copy those out and deinstall the kit if you don't want it around.

  3. Use the instsrv.exe program to install the srvany.exe program by using it like this from the command-line:
    instsrv.exe FitNesse "\srvany.exe" -a MYMACHINE\fitnesse -p soSecret

  4. Run the regedit.exe program to set the last parameters.

  5. Find the key HKEY_LOCAL_MACHINE\SYSTEM\CurrentControlSet[?]\Services\FitNesse

  6. Create a subkey with the name Parameters

  7. In the parameters key, create a string value called Application and set its value to the full path of the java.exe file. For me it was : C:\Program Files\Java\jre1.5.0_04\bin\java.exe.

  8. Create another string value called AppDirectory and set its value to the path where you want the executable to run. The directory where your FitNesse files are located : c:\Program Files\FitNesse

  9. Create a last string value called AppParameters containing the parameters passed to the java executable above : -cp fitnesse.jar -Xrs fitnesse.FitNesse -p 8080

  10. Open the service control panel and start the service.

You can now write the same fixtures and reference them from Fit or Fitnesse. I hope you find these instructions helpful. Happy testing.

-David