From 0cd8f97bd8278eade7e2dee9f9494997c6794b2a Mon Sep 17 00:00:00 2001 From: Richard Spink Date: Sun, 3 May 2026 16:46:37 -0600 Subject: [PATCH] Improve contributor docs and test hygiene --- EngineTests/EngineTests.csproj | 8 +-- EngineTests/GameData/MultiTurnDealsTest.cs | 54 +++++--------------- EngineTests/GameData/SaveTest.cs | 17 ++----- EngineTests/GameData/UnitPrototypeTest.cs | 27 +++------- EngineTests/Utils/Civ3TestData.cs | 30 +++++++++++ README.md | 6 +-- doc/dev_environment.md | 58 ++++++++++------------ 7 files changed, 85 insertions(+), 115 deletions(-) create mode 100644 EngineTests/Utils/Civ3TestData.cs diff --git a/EngineTests/EngineTests.csproj b/EngineTests/EngineTests.csproj index d960341bd..fa5ca4cf1 100644 --- a/EngineTests/EngineTests.csproj +++ b/EngineTests/EngineTests.csproj @@ -7,9 +7,9 @@ - + - + runtime; build; native; contentfiles; analyzers; buildtransitive @@ -19,7 +19,9 @@ runtime; build; native; contentfiles; analyzers; buildtransitive all - + + + diff --git a/EngineTests/GameData/MultiTurnDealsTest.cs b/EngineTests/GameData/MultiTurnDealsTest.cs index 5f9803f49..6df1fa951 100644 --- a/EngineTests/GameData/MultiTurnDealsTest.cs +++ b/EngineTests/GameData/MultiTurnDealsTest.cs @@ -12,13 +12,7 @@ public class MultiTurnDealTest : RemoteSaveLoader { private const string SAVES_FOLDER = "saves/multi-turn-deals"; [Fact] public async void TestMultiTurnDeal_Save_A() { - // When running the tests via github actions, civ3 isn't installed so we - // can't load the default bic. - // - // See https://docs.github.com/en/actions/writing-workflows/choosing-what-your-workflow-does/store-information-in-variables#default-environment-variables - // for a full list of env vars. - string is_on_github = System.Environment.GetEnvironmentVariable("CI"); - if (is_on_github != null) { + if (Civ3TestData.ShouldSkipCiv3DependentTests()) { return; } @@ -97,13 +91,7 @@ public async void TestMultiTurnDeal_Save_A() { [Fact] public async void TestMultiTurnDeal_Save_B() { - // When running the tests via github actions, civ3 isn't installed so we - // can't load the default bic. - // - // See https://docs.github.com/en/actions/writing-workflows/choosing-what-your-workflow-does/store-information-in-variables#default-environment-variables - // for a full list of env vars. - string is_on_github = System.Environment.GetEnvironmentVariable("CI"); - if (is_on_github != null) { + if (Civ3TestData.ShouldSkipCiv3DependentTests()) { return; } @@ -207,13 +195,7 @@ public async void TestMultiTurnDeal_Save_B() { [Fact] public async void TestMultiTurnDeal_Save_C() { - // When running the tests via github actions, civ3 isn't installed so we - // can't load the default bic. - // - // See https://docs.github.com/en/actions/writing-workflows/choosing-what-your-workflow-does/store-information-in-variables#default-environment-variables - // for a full list of env vars. - string is_on_github = System.Environment.GetEnvironmentVariable("CI"); - if (is_on_github != null) { + if (Civ3TestData.ShouldSkipCiv3DependentTests()) { return; } @@ -363,13 +345,7 @@ public async void TestMultiTurnDeal_Save_C() { [Fact] public async void TestMultiTurnDeal_Save_D() { - // When running the tests via github actions, civ3 isn't installed so we - // can't load the default bic. - // - // See https://docs.github.com/en/actions/writing-workflows/choosing-what-your-workflow-does/store-information-in-variables#default-environment-variables - // for a full list of env vars. - string is_on_github = System.Environment.GetEnvironmentVariable("CI"); - if (is_on_github != null) { + if (Civ3TestData.ShouldSkipCiv3DependentTests()) { return; } @@ -474,13 +450,10 @@ public async void TestMultiTurnDeal_Save_D() { [Fact] public async void TestMultiTurnDeal_Save_E() { - // When running the tests via github actions, civ3 isn't installed so we - // can't load the default bic. - // - // See https://docs.github.com/en/actions/writing-workflows/choosing-what-your-workflow-does/store-information-in-variables#default-environment-variables - // for a full list of env vars. - string is_on_github = System.Environment.GetEnvironmentVariable("CI"); - if (is_on_github != null) { + if (Civ3TestData.ShouldSkipCiv3DependentTests( + "Conquests/Scenarios/8 MP Napoleonic Europe.biq", + "Conquests/Conquests/Napoleonic Europe/Text/PediaIcons.txt" + )) { return; } @@ -634,13 +607,10 @@ public async void TestMultiTurnDeal_Save_E() { [Fact] public async void TestMultiTurnDeal_Save_F() { - // When running the tests via github actions, civ3 isn't installed so we - // can't load the default bic. - // - // See https://docs.github.com/en/actions/writing-workflows/choosing-what-your-workflow-does/store-information-in-variables#default-environment-variables - // for a full list of env vars. - string is_on_github = System.Environment.GetEnvironmentVariable("CI"); - if (is_on_github != null) { + if (Civ3TestData.ShouldSkipCiv3DependentTests( + "Conquests/Scenarios/8 MP Napoleonic Europe.biq", + "Conquests/Conquests/Napoleonic Europe/Text/PediaIcons.txt" + )) { return; } diff --git a/EngineTests/GameData/SaveTest.cs b/EngineTests/GameData/SaveTest.cs index 41d2494f6..983c54252 100644 --- a/EngineTests/GameData/SaveTest.cs +++ b/EngineTests/GameData/SaveTest.cs @@ -9,6 +9,7 @@ using C7Engine.Lua; using C7GameData; using C7GameData.Save; +using EngineTests.Utils; using Newtonsoft.Json.Linq; using QueryCiv3; using Xunit; @@ -452,13 +453,7 @@ public void TurnTimeCalculations() { [Fact] public async void LoadSampleSaves() { - // When running the tests via github actions, civ3 isn't installed so we - // can't load the default bic. - // - // See https://docs.github.com/en/actions/writing-workflows/choosing-what-your-workflow-does/store-information-in-variables#default-environment-variables - // for a full list of env vars. - string is_on_github = System.Environment.GetEnvironmentVariable("CI"); - if (is_on_github != null) { return; } + if (Civ3TestData.ShouldSkipCiv3DependentTests()) { return; } string savesPath = PathUtils.getDataPath("saves"); Directory.CreateDirectory(savesPath); @@ -496,13 +491,7 @@ public async void LoadSampleSaves() { [Fact] public void LoadAllConquestScenarios() { - // When running the tests via github actions, civ3 isn't installed so we can't - // check the conquests directories. - // - // See https://docs.github.com/en/actions/writing-workflows/choosing-what-your-workflow-does/store-information-in-variables#default-environment-variables - // for a full list of env vars. - string is_on_github = System.Environment.GetEnvironmentVariable("CI"); - if (is_on_github != null) { return; } + if (Civ3TestData.ShouldSkipCiv3DependentTests()) { return; } string[] singleplayerScenarios = { "1 Mesopotamia.biq", diff --git a/EngineTests/GameData/UnitPrototypeTest.cs b/EngineTests/GameData/UnitPrototypeTest.cs index 1907fa217..e32d912de 100644 --- a/EngineTests/GameData/UnitPrototypeTest.cs +++ b/EngineTests/GameData/UnitPrototypeTest.cs @@ -18,13 +18,7 @@ public async void UnitAvailability_SAV() { // This tests a Conquests game with Conquests rules from a .SAV file #region setup - // When running the tests via github actions, civ3 isn't installed so we - // can't load the default bic. - // - // See https://docs.github.com/en/actions/writing-workflows/choosing-what-your-workflow-does/store-information-in-variables#default-environment-variables - // for a full list of env vars. - string is_on_github = System.Environment.GetEnvironmentVariable("CI"); - if (is_on_github != null) { + if (Civ3TestData.ShouldSkipCiv3DependentTests()) { return; } @@ -263,13 +257,7 @@ public async void UnitAvailability_SAV() { public async void UnitAvailability_JSON() { // This tests a Conquests game with Conquests rules from a .json file #region setup - // When running the tests via github actions, civ3 isn't installed so we - // can't load the default bic. - // - // See https://docs.github.com/en/actions/writing-workflows/choosing-what-your-workflow-does/store-information-in-variables#default-environment-variables - // for a full list of env vars. - string is_on_github = System.Environment.GetEnvironmentVariable("CI"); - if (is_on_github != null) { + if (Civ3TestData.ShouldSkipCiv3DependentTests()) { return; } @@ -451,13 +439,10 @@ public async void UnitAvailability_SAV() { // This tests a Conquests scenario with custom rules #region setup - // When running the tests via github actions, civ3 isn't installed so we - // can't load the default bic. - // - // See https://docs.github.com/en/actions/writing-workflows/choosing-what-your-workflow-does/store-information-in-variables#default-environment-variables - // for a full list of env vars. - string is_on_github = System.Environment.GetEnvironmentVariable("CI"); - if (is_on_github != null) { + if (Civ3TestData.ShouldSkipCiv3DependentTests( + "Conquests/Conquests/4 Middle Ages.biq", + "Conquests/Conquests/Middle Ages/Text/PediaIcons.txt" + )) { return; } string scenarioBiqPath = Path.Combine(Civ3Location.GetCiv3Path(), "Conquests", "Conquests", "4 Middle Ages.biq"); diff --git a/EngineTests/Utils/Civ3TestData.cs b/EngineTests/Utils/Civ3TestData.cs new file mode 100644 index 000000000..77c410544 --- /dev/null +++ b/EngineTests/Utils/Civ3TestData.cs @@ -0,0 +1,30 @@ +using System; +using System.IO; +using System.Linq; +using QueryCiv3; + +namespace EngineTests.Utils; + +public static class Civ3TestData { + private static readonly string[] DefaultRequiredFiles = { + "Conquests/conquests.biq", + "Conquests/Text/PediaIcons.txt", + }; + + public static bool ShouldSkipCiv3DependentTests(params string[] requiredRelativePaths) { + if (Environment.GetEnvironmentVariable("CI") != null) { + return true; + } + + string[] requiredFiles = DefaultRequiredFiles.Concat(requiredRelativePaths).ToArray(); + return requiredFiles.Any(relativePath => !File.Exists(GetCiv3Path(relativePath))); + } + + private static string GetCiv3Path(string relativePath) { + string normalizedPath = relativePath + .Replace('\\', Path.DirectorySeparatorChar) + .Replace('/', Path.DirectorySeparatorChar); + + return Path.Combine(Civ3Location.GetCiv3Path(), normalizedPath); + } +} diff --git a/README.md b/README.md index 9e68a4d1a..ca57ef635 100644 --- a/README.md +++ b/README.md @@ -16,15 +16,15 @@ ## Status -The latest stable version can be downloaded from the [Releases page](https://github.com/C7-Game/Prototype/releases). Current information on installation and features can always be found on the [project homepage.](https://www.openciv3.org/) +The latest stable version can be downloaded from the [Releases page](https://github.com/C7-Game/OpenCiv3/releases). Current information on installation and features can always be found on the [project homepage.](https://www.openciv3.org/) OpenCiv3 is in a pre-alpha state. It is a rudimentary playable game but lacking many mechanics and late-game content, and errors are likely. Keep up with our development for the latest updates and opportunities to contribute! ## Contributing -Find the project interesting and want to contribute? See [Contributing](https://github.com/C7-Game/Prototype/wiki/Contributing) on our Wiki for more information! At the moment, additional developer support is the most-needed asset, but all sorts of help (art, writing, project management, playtesting) could be useful. +Find the project interesting and want to contribute? See [Contributing](https://github.com/C7-Game/OpenCiv3/wiki/Contributing) on our Wiki for more information! At the moment, additional developer support is the most-needed asset, but all sorts of help (art, writing, project management, playtesting) could be useful. -To set up a working development environment, see [Developing and Setting Up IDEs](https://github.com/C7-Game/Prototype/wiki/Developing-and-Setting-Up-IDEs). +To set up a working development environment, see [Developing and Setting Up IDEs](https://github.com/C7-Game/OpenCiv3/wiki/Developing-and-Setting-Up-IDEs). ## What are those subfolders? diff --git a/doc/dev_environment.md b/doc/dev_environment.md index f09914ee1..4615c74ed 100644 --- a/doc/dev_environment.md +++ b/doc/dev_environment.md @@ -1,56 +1,50 @@ # Development Environment -This document provides steps to set up a working C7 development environment. +This document provides steps to set up a working OpenCiv3 development environment. Some source paths still use the older `C7` name; the Godot project and C# solution are in the `C7` directory. # Requirements ## .NET SDK -Download [.NET 6.0](https://dotnet.microsoft.com/en-us/download/dotnet). +Download the [.NET SDK](https://dotnet.microsoft.com/en-us/download), version 8.0 or higher. The projects currently target `net8.0`. ## Godot -Install the Mono version of [Godot](https://godotengine.org/download). This includes the Godot IDE which is useful for building C7 and in some cases developing UI, but it is not recommended for C# code editing. +Install the [.NET version of Godot 4.4](https://godotengine.org/download). The Godot editor is useful for importing the project, running the game, wiring scene events, and creating UI, but a full C# IDE is still recommended for code editing. + +The first time you check out OpenCiv3, import `C7/project.godot` from the Godot Project Manager. Godot will build the C# project before running it. # IDEs -There are two free IDEs recommended for C# development. Follow the steps below for setting up a working development environment in these editors and troubleshooting for common issues. Another alternative is to use [JetBrains Rider](https://www.jetbrains.com/rider/download/), a commercial IDE for C# development. There is a -[CFC thread](https://forums.civfanatics.com/threads/dev-jetbrains-rider-impressions.675190/) on Rider that may provide additional information on setting it up. +Most OpenCiv3 development is C#, so use Visual Studio Code or JetBrains Rider alongside the Godot editor. Visual Studio 2019 is no longer a supported setup for current Godot 4/.NET development. ## Visual Studio Code Follow the [official guide](https://code.visualstudio.com/docs/setup/setup-overview#_cross-platform) to install Visual Studio Code for your platform. -Next, install the following plugins from the marketplace: -1. [C# for Visual Studio Code](https://marketplace.visualstudio.com/items?itemName=ms-dotnettools.csharp) - this provides syntax highlighting, IntelliSense, find references, and other nice IDE-like features for C#. -2. [C# Tools for Godot](https://marketplace.visualstudio.com/items?itemName=neikeq.godot-csharp-vscode) - this enables launching C7 from VS Code and debugging +Next, install the following extensions from the marketplace: +1. [C# for Visual Studio Code](https://marketplace.visualstudio.com/items?itemName=ms-dotnettools.csharp) - this provides syntax highlighting, IntelliSense, find references, and other IDE-like features for C#. +2. [C# Tools for Godot](https://marketplace.visualstudio.com/items?itemName=neikeq.godot-csharp-vscode) - this helps with launching and debugging Godot C# projects from VS Code. -Finally, set up code formatting. For Visual Studio Code, formatting is done with OmniSharp and configured by the `.editorconfig` file. In order to configure OmniSharp, do the following: -1. In your home directory, create `~/.omnisharp/omnisharp.json` with the following contents -``` -{ - "RoslynExtensionsOptions": { - "enableAnalyzersSupport": true, - }, - "FormattingOptions": { - "enableEditorConfigSupport": true, - } -} -``` -2. Add the following options to your VS Code `settings.json` (either workspace settings or your user level settings) -``` +Finally, set up code formatting. The repository uses `.editorconfig`; VS Code can honor it through the C# extension settings. Add the following options to your VS Code `settings.json` if they are not already enabled: + +```json "omnisharp.enableMsBuildLoadProjectsOnDemand": true, "omnisharp.enableEditorConfigSupport": true, "omnisharp.enableRoslynAnalyzers": true, -``` -3. Optionally but recommended, add this option to your VS Code `settings.json` to enable formatting on save -``` "[csharp]": { - "editor.formatOnSave": true, + "editor.formatOnSave": true } ``` ### Troubleshooting -- Linting or IntelliSense are completely broken - - try adding `"omnisharp.useGlobalMono": "always"` to `settings.json` - - you may need to rebuild the entire project through the Godot IDE +- If linting or IntelliSense are completely broken, rebuild the project through the Godot editor and restart VS Code. +- If command-line builds fail before Godot has imported the project, open `C7/project.godot` in the Godot editor once, let it finish the initial build, and try again. + +## JetBrains Rider +Rider has strong C# support and good Godot integration. Install Rider, add the Godot Support plugin, and open `C7/C7.sln`. Use a Godot 4 `.NET Executable` run configuration that points at your local Godot executable and the `C7` project directory. -## Visual Studio 2019 Community Edition -It's important to use Visual Studio 2019, as you cannot run/debug Godot from Visual Studio 2022 yet, and 2019 was the first version to be supported. +# Build and Test +From the repository root: + +```bash +dotnet build C7/C7.sln +dotnet test C7/C7.sln --logger "console;verbosity=detailed" +``` -The Visual Studio solution file is already aware of the `.editorconfig` file, so no further setup is required. +Some tests load Civilization III assets. Set `CIV3_HOME` to the top-level Civilization III install folder if you want to run those locally.