Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

ALM - Project Migration #3972

Merged
merged 3 commits into from
Oct 28, 2024
Merged
Show file tree
Hide file tree
Changes from all 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
8 changes: 7 additions & 1 deletion Ginger/Ginger/ALM/Repository/RQMRepository.cs
Original file line number Diff line number Diff line change
Expand Up @@ -30,6 +30,7 @@ limitations under the License.
using System.IO;
using System.IO.Compression;
using System.Linq;
using System.Windows.Input;
using static GingerCoreNET.ALMLib.ALMIntegrationEnums;

namespace Ginger.ALM.Repository
Expand Down Expand Up @@ -59,9 +60,10 @@ public override bool ShowImportReviewPage(string importDestinationFolderPath, ob
importDestinationFolderPath = WorkSpace.Instance.Solution.BusinessFlowsMainFolder;
}
// get activities groups
Mouse.OverrideCursor = System.Windows.Input.Cursors.Wait;
RQMImportReviewPage win = new RQMImportReviewPage(RQMConnect.Instance.GetRQMTestPlanFullData(ALMCore.DefaultAlmConfig.ALMServerURL, ALMCore.DefaultAlmConfig.ALMUserName, ALMCore.DefaultAlmConfig.ALMPassword, ALMCore.DefaultAlmConfig.ALMProjectKey, (RQMTestPlan)selectedTestPlan), importDestinationFolderPath);
win.ShowAsWindow();

Mouse.OverrideCursor = null;
Comment on lines +63 to +66
Copy link
Contributor

Choose a reason for hiding this comment

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

⚠️ Potential issue

Add try-finally block for cursor management

The cursor should be reset even if an exception occurs during the RQM operation. Consider wrapping the code in a try-finally block.

Here's the suggested fix:

-            Mouse.OverrideCursor = System.Windows.Input.Cursors.Wait;
-            RQMImportReviewPage win = new RQMImportReviewPage(RQMConnect.Instance.GetRQMTestPlanFullData(ALMCore.DefaultAlmConfig.ALMServerURL, ALMCore.DefaultAlmConfig.ALMUserName, ALMCore.DefaultAlmConfig.ALMPassword, ALMCore.DefaultAlmConfig.ALMProjectKey, (RQMTestPlan)selectedTestPlan), importDestinationFolderPath);
-            win.ShowAsWindow();
-            Mouse.OverrideCursor = null;
+            try
+            {
+                Mouse.OverrideCursor = System.Windows.Input.Cursors.Wait;
+                RQMImportReviewPage win = new RQMImportReviewPage(RQMConnect.Instance.GetRQMTestPlanFullData(ALMCore.DefaultAlmConfig.ALMServerURL, ALMCore.DefaultAlmConfig.ALMUserName, ALMCore.DefaultAlmConfig.ALMPassword, ALMCore.DefaultAlmConfig.ALMProjectKey, (RQMTestPlan)selectedTestPlan), importDestinationFolderPath);
+                win.ShowAsWindow();
+            }
+            finally
+            {
+                Mouse.OverrideCursor = null;
+            }
📝 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
Mouse.OverrideCursor = System.Windows.Input.Cursors.Wait;
RQMImportReviewPage win = new RQMImportReviewPage(RQMConnect.Instance.GetRQMTestPlanFullData(ALMCore.DefaultAlmConfig.ALMServerURL, ALMCore.DefaultAlmConfig.ALMUserName, ALMCore.DefaultAlmConfig.ALMPassword, ALMCore.DefaultAlmConfig.ALMProjectKey, (RQMTestPlan)selectedTestPlan), importDestinationFolderPath);
win.ShowAsWindow();
Mouse.OverrideCursor = null;
try
{
Mouse.OverrideCursor = System.Windows.Input.Cursors.Wait;
RQMImportReviewPage win = new RQMImportReviewPage(RQMConnect.Instance.GetRQMTestPlanFullData(ALMCore.DefaultAlmConfig.ALMServerURL, ALMCore.DefaultAlmConfig.ALMUserName, ALMCore.DefaultAlmConfig.ALMPassword, ALMCore.DefaultAlmConfig.ALMProjectKey, (RQMTestPlan)selectedTestPlan), importDestinationFolderPath);
win.ShowAsWindow();
}
finally
{
Mouse.OverrideCursor = null;
}

return true;
}

Expand Down Expand Up @@ -175,6 +177,7 @@ public override bool ImportSelectedTests(string importDestinationPath, IEnumerab

public override void UpdateActivitiesGroup(ref BusinessFlow businessFlow, List<Tuple<string, string>> TCsIDs)
{
Mouse.OverrideCursor = System.Windows.Input.Cursors.Wait;
foreach (RQMTestPlan testPlan in RQMConnect.Instance.GetRQMTestPlansByProject(ALMCore.DefaultAlmConfig.ALMServerURL, ALMCore.DefaultAlmConfig.ALMUserName, ALMCore.DefaultAlmConfig.ALMPassword, ALMCore.DefaultAlmConfig.ALMProjectName, System.IO.Path.Combine(WorkSpace.Instance.Solution.Folder, @"Documents\ALM\RQM_Configs")).OrderByDescending(item => item.CreationDate))
{
if (testPlan.RQMID == ExportToRQM.GetExportedIDString(businessFlow.ExternalIdCalCulated, "RQMID"))
Expand All @@ -183,10 +186,12 @@ public override void UpdateActivitiesGroup(ref BusinessFlow businessFlow, List<T
((RQMCore)ALMIntegration.Instance.AlmCore).UpdatedRQMTestInBF(ref businessFlow, currentRQMTestPlan, TCsIDs.Select(x => x.Item1.ToString()).ToList());
}
}
Mouse.OverrideCursor = null;
}

public override void UpdateBusinessFlow(ref BusinessFlow businessFlow)
{
Mouse.OverrideCursor = System.Windows.Input.Cursors.Wait;
foreach (RQMTestPlan testPlan in RQMConnect.Instance.GetRQMTestPlansByProject(ALMCore.DefaultAlmConfig.ALMServerURL, ALMCore.DefaultAlmConfig.ALMUserName, ALMCore.DefaultAlmConfig.ALMPassword, ALMCore.DefaultAlmConfig.ALMProjectName, System.IO.Path.Combine(WorkSpace.Instance.Solution.Folder, @"Documents\ALM\RQM_Configs")).OrderByDescending(item => item.CreationDate))
{
if (testPlan.RQMID == ExportToRQM.GetExportedIDString(businessFlow.ExternalIdCalCulated, "RQMID"))
Expand All @@ -195,6 +200,7 @@ public override void UpdateBusinessFlow(ref BusinessFlow businessFlow)
((RQMCore)ALMIntegration.Instance.AlmCore).UpdateBusinessFlow(ref businessFlow, currentRQMTestPlan);
}
}
Mouse.OverrideCursor = null;
}

public override void ExportBfActivitiesGroupsToALM(BusinessFlow businessFlow, ObservableList<ActivitiesGroup> grdActivitiesGroups)
Expand Down
Binary file removed Ginger/GingerCore/DLLs/ACL_Data_Contract.dll
Binary file not shown.
Binary file removed Ginger/GingerCore/DLLs/ALMRestClient.dll
Binary file not shown.
Binary file removed Ginger/GingerCore/DLLs/ALMRestClientStd.dll
Binary file not shown.
Binary file removed Ginger/GingerCore/DLLs/ALM_CommonStd.dll
Binary file not shown.
Binary file removed Ginger/GingerCore/DLLs/AlmDataContractsStd.dll
Binary file not shown.
Binary file removed Ginger/GingerCore/DLLs/AlmRepositoryStd.dll
Binary file not shown.
Binary file removed Ginger/GingerCore/DLLs/OctaneRepositoryStd.dll
Binary file not shown.
Binary file removed Ginger/GingerCore/DLLs/OctaneSdkStandard.dll
Binary file not shown.
Binary file removed Ginger/GingerCore/DLLs/OctaneStdSDK.dll
Binary file not shown.
Binary file removed Ginger/GingerCore/DLLs/Octane_Repository.dll
Binary file not shown.
Binary file removed Ginger/GingerCore/DLLs/QCRestClient.dll
Binary file not shown.
Binary file removed Ginger/GingerCore/DLLs/QCRestClientStd.dll
Binary file not shown.
Binary file removed Ginger/GingerCore/DLLs/QTestAPI.dll
Binary file not shown.
Binary file removed Ginger/GingerCore/DLLs/QTestAPIStd.dll
Binary file not shown.
Binary file removed Ginger/GingerCore/DLLs/RQMExportStd.dll
Binary file not shown.
Binary file removed Ginger/GingerCore/DLLs/RQM_RepositoryStd.dll
Binary file not shown.
Binary file removed Ginger/GingerCore/DLLs/ZephyrEntStdSDK.dll
Binary file not shown.
Binary file removed Ginger/GingerCore/DLLs/Zepyhr_Ent_Repository_Std.dll
Binary file not shown.
66 changes: 9 additions & 57 deletions Ginger/GingerCore/GingerCore.csproj
Original file line number Diff line number Diff line change
Expand Up @@ -40,6 +40,12 @@
<PropertyGroup>
<PlatformTarget>AnyCPU</PlatformTarget>
</PropertyGroup>
<ItemGroup>
<EmbeddedResource Remove="Environments\**" />
<EmbeddedResource Remove="Plugins\**" />
<None Remove="Environments\**" />
<None Remove="Plugins\**" />
</ItemGroup>
<ItemGroup>
<Reference Include="ACL_Data_Contract">
<HintPath>DLLs\ACL_Data_Contract.dll</HintPath>
Expand Down Expand Up @@ -75,6 +81,9 @@
<Reference Include="OctaneRepositoryStd">
<HintPath>DLLs\OctaneRepositoryStd.dll</HintPath>
</Reference>
<Reference Include="OctaneSdkStandard">
<HintPath>..\GingerCoreNET\DLLS\OctaneSdkStandard.dll</HintPath>
</Reference>
<Reference Include="Open3270, Version=1.5.0.1, Culture=neutral, processorArchitecture=MSIL">
<SpecificVersion>False</SpecificVersion>
<HintPath>..\Ginger\DLLs\Open3270.dll</HintPath>
Expand Down Expand Up @@ -255,43 +264,6 @@
<Compile Include="Actions\XML\ActXMLProcessing.cs" />
<Compile Include="Actions\XML\XMLProcessor.cs" />
<Compile Include="ActOcr.cs" />
<Compile Include="ALM\QtestCore.cs" />
<Compile Include="ALM\Qtest\ImportFromQtest.cs" />
<Compile Include="ALM\QCRestAPICore.cs" />
<Compile Include="ALM\QCRestAPI\ExportToQCRestAPI.cs" />
<Compile Include="ALM\QCRestAPI\ImportFromQCRest.cs" />
<Compile Include="ALM\QCRestAPI\QCRestAPIConnect.cs" />
<Compile Include="ALM\QC\ExportToQC.cs" />
<Compile Include="ALM\QCCore.cs" />
<Compile Include="ALM\QC\ImportFromQC.cs" />
<Compile Include="ALM\QC\QCConnect.cs" />
<Compile Include="ALM\Qtest\QtestTestRun.cs" />
<Compile Include="ALM\Qtest\QtestTestSuite.cs" />
<Compile Include="ALM\Qtest\QtestTest.cs" />
<Compile Include="ALM\Qtest\QtestTestParameter.cs" />
<Compile Include="ALM\Qtest\QtestTestStep.cs" />
<Compile Include="ALM\Qtest\QtestConnect.cs" />
<Compile Include="ALM\RallyCore.cs" />
<Compile Include="ALM\Rally\ImportFromRally.cs" />
<Compile Include="ALM\Rally\RallyConnect.cs" />
<Compile Include="ALM\Rally\RallyStep.cs" />
<Compile Include="ALM\Rally\RallyTestCase.cs" />
<Compile Include="ALM\Rally\RallyTestParameter.cs" />
<Compile Include="ALM\Rally\RallyTestPlan.cs" />
<Compile Include="ALM\RQMCore.cs" />
<Compile Include="ALM\RQM\ExportToRQM.cs" />
<Compile Include="ALM\RQM\ImportFromRQM.cs" />
<Compile Include="ALM\RQM\RQMTestSuiteResults.cs" />
<Compile Include="ALM\RQM\RQMTestSuiteExecutionRecord.cs" />
<Compile Include="ALM\RQM\RQMTestSuite.cs" />
<Compile Include="ALM\RQM\RQMTestParameter.cs" />
<Compile Include="ALM\RQM\RQMStep.cs" />
<Compile Include="ALM\RQM\RQMExecutionRecord.cs" />
<Compile Include="ALM\RQM\RQMTestScript.cs" />
<Compile Include="ALM\RQM\RQMTestCase.cs" />
<Compile Include="ALM\RQM\RQMFieldsMappingConfig.cs" />
<Compile Include="ALM\RQM\RQMTestPlan.cs" />
<Compile Include="ALM\RQM\RQMConnect.cs" />
<Compile Include="DataSource\DataSourceTableColumn.cs" />
<Compile Include="Common\Devices\DeviceConfig.cs" />
<Compile Include="Common\Devices\DeviceButton.cs" />
Expand Down Expand Up @@ -320,7 +292,6 @@
<Compile Include="Drivers\MainFrame\MainFrameUIHelper.cs" />
<Compile Include="Drivers\MainFrame\Terminal.cs" />
<Compile Include="Drivers\PBDriver\HTMLHelper.cs" />
<Compile Include="External\JsonExternalItemField.cs" />
<Compile Include="GeneralLib\BindingHandler.cs" />
<Compile Include="GeneralLib\ComboEnumItem.cs" />
<Compile Include="GeneralLib\ComboGroupedEnumItem.cs" />
Expand All @@ -337,7 +308,6 @@
<Compile Include="GeneralLib\ProcessExtension.cs" />
<Compile Include="GingerOCR\GingerOcrOperations.cs" />
<Compile Include="Helpers\HTMLHelper.cs" />
<Compile Include="Properties\Annotations.cs" />
<Compile Include="Properties\Resources.Designer.cs">
<AutoGen>True</AutoGen>
<DesignTime>True</DesignTime>
Expand Down Expand Up @@ -415,19 +385,6 @@
<Resource Include="tessdata\pdf.ttf">
<CopyToOutputDirectory>Always</CopyToOutputDirectory>
</Resource>
<Resource Include="ALM\RQM\RQMServerConfigurationsPackage\RQMSettings.xml">
<SubType>Designer</SubType>
<CopyToOutputDirectory>PreserveNewest</CopyToOutputDirectory>
</Resource>
<Resource Include="ALM\RQM\RQMServerConfigurationsPackage\RQM_Export\Export_Settings.xml" />
<Resource Include="ALM\RQM\RQMServerConfigurationsPackage\RQM_Export\QM\fa1qm1\executionRecord.xml" />
<Resource Include="ALM\RQM\RQMServerConfigurationsPackage\RQM_Export\QM\fa1qm1\ExecutionResult.xml" />
<Resource Include="ALM\RQM\RQMServerConfigurationsPackage\RQM_Export\QM\fa1qm1\TestCase.xml" />
<Resource Include="ALM\RQM\RQMServerConfigurationsPackage\RQM_Export\QM\fa1qm1\TestPlan.xml" />
<Resource Include="ALM\RQM\RQMServerConfigurationsPackage\RQM_Export\QM\fa1qm1\TestScript.xml" />
<Resource Include="ALM\RQM\RQMServerConfigurationsPackage\RQM_Import\RQM_ImportConfigs_Template.xml">
<CopyToOutputDirectory>Always</CopyToOutputDirectory>
</Resource>
<None Include="Resources\%40EmptyStart_16x16.gif" />
<None Include="Resources\%40Star_16x16.gif" />
<None Include="Resources\%40StarGray_16x16.gif" />
Expand All @@ -442,12 +399,7 @@
<ItemGroup>
<Folder Include="Actions\REST\" />
<Folder Include="Actions\WebServices\" />
<Folder Include="ALM\RQM\RQMServerConfigurationsPackage\RQM_Export\CCM\fa1qm1\" />
<Folder Include="ALM\RQM\RQMServerConfigurationsPackage\RQM_Export\RM\" />
<Folder Include="ALM\RQM\RQMServerConfigurationsPackage\RQM_Fields\" />
<Folder Include="Drivers\JavaDriverLib\GingerJavaAgent\bin\com\amdocs\ginger\ASCFPack\" />
<Folder Include="Environments\" />
<Folder Include="Plugins\Jenkins\" />
</ItemGroup>
<ItemGroup>
<Resource Include="Resources\Const.png" />
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -27,6 +27,7 @@ limitations under the License.
using GingerCore.ALM.Qtest;
using GingerCore.Environments;
using GingerCoreNET.ALMLib;
using GingerCoreNET.GeneralLib;
using GingerCoreNET.SolutionRepositoryLib.RepositoryObjectsLib.PlatformsLib;
using System;
using System.Collections.Generic;
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -18,6 +18,7 @@ limitations under the License.

using amdocs.ginger.GingerCoreNET;
using Amdocs.Ginger.Common;
using GingerCoreNET.GeneralLib;
using System;
using System.IO;

Expand Down Expand Up @@ -76,7 +77,7 @@ public bool ConnectALMServer()
connObj.Configuration.ApiKeyPrefix.Add("Authorization", tokenType);

string almConfigPackageFolderPathCalculated = WorkSpace.Instance.Solution.SolutionOperations.ConvertSolutionRelativePath(ALMCore.DefaultAlmConfig.ALMConfigPackageFolderPath);
if (GingerCore.General.IsConfigPackageExists(almConfigPackageFolderPathCalculated, GingerCoreNET.ALMLib.ALMIntegrationEnums.eALMType.Qtest))
if (General.IsConfigPackageExists(almConfigPackageFolderPathCalculated, GingerCoreNET.ALMLib.ALMIntegrationEnums.eALMType.Qtest))
{
connObj.Configuration.MyAPIConfig.LoadSettingsFromConfig(Path.Combine(almConfigPackageFolderPathCalculated, "QTestSettings", "QTestSettings.json"));
}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -403,7 +403,7 @@ public RQMTestPlan GetRQMTestPlanFullData(string RQMServerUrl, string RQMUserNam
try
{
System.Diagnostics.Trace.WriteLine("in GetRQMTestPlanFullData :");
Mouse.OverrideCursor = System.Windows.Input.Cursors.Wait;

GetRQMProjectListConfiguration();
if (RQMProjectListConfig != null)
{
Expand Down Expand Up @@ -474,8 +474,7 @@ public RQMTestPlan GetRQMTestPlanFullData(string RQMServerUrl, string RQMUserNam
{
Reporter.ToLog(eLogLevel.ERROR, $"Error while trying to import selected RQM test plan, RQM_ImportConfigs_Template.xml wasn't found");
}

Mouse.OverrideCursor = null;

}
catch (Exception ex)
{
Expand Down
20 changes: 20 additions & 0 deletions Ginger/GingerCoreNET/GeneralLib/General.cs
Original file line number Diff line number Diff line change
Expand Up @@ -656,6 +656,26 @@ public static bool CreateGingerOpsConfiguration()
return false;
}
}

public static bool IsConfigPackageExists(string PackagePath, GingerCoreNET.ALMLib.ALMIntegrationEnums.eALMType eALMType)
{
string settingsFolder = string.Empty;
settingsFolder = eALMType switch
{
GingerCoreNET.ALMLib.ALMIntegrationEnums.eALMType.Jira => "JiraSettings",
GingerCoreNET.ALMLib.ALMIntegrationEnums.eALMType.Qtest => "QTestSettings",
_ => "JiraSettings",
};
Comment on lines +663 to +668
Copy link
Contributor

Choose a reason for hiding this comment

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

⚠️ Potential issue

Revise the switch expression's default case.

The current default case returns "JiraSettings" which could be misleading for unsupported ALM types. Consider either:

  1. Throwing an exception for unsupported types
  2. Using a more appropriate default folder name

Apply this diff:

 settingsFolder = eALMType switch
 {
     GingerCoreNET.ALMLib.ALMIntegrationEnums.eALMType.Jira => "JiraSettings",
     GingerCoreNET.ALMLib.ALMIntegrationEnums.eALMType.Qtest => "QTestSettings",
-    _ => "JiraSettings",
+    _ => throw new ArgumentException($"Unsupported ALM type: {eALMType}", nameof(eALMType))
 };
📝 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
settingsFolder = eALMType switch
{
GingerCoreNET.ALMLib.ALMIntegrationEnums.eALMType.Jira => "JiraSettings",
GingerCoreNET.ALMLib.ALMIntegrationEnums.eALMType.Qtest => "QTestSettings",
_ => "JiraSettings",
};
settingsFolder = eALMType switch
{
GingerCoreNET.ALMLib.ALMIntegrationEnums.eALMType.Jira => "JiraSettings",
GingerCoreNET.ALMLib.ALMIntegrationEnums.eALMType.Qtest => "QTestSettings",
_ => throw new ArgumentException($"Unsupported ALM type: {eALMType}", nameof(eALMType))
};

Comment on lines +662 to +668
Copy link
Contributor

Choose a reason for hiding this comment

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

🛠️ Refactor suggestion

Consider improving maintainability of settings folder names.

The hardcoded folder names could make maintenance difficult. Consider:

  1. Moving them to constants or configuration
  2. Using a consistent naming pattern

Apply this diff to improve maintainability:

+    private static readonly Dictionary<GingerCoreNET.ALMLib.ALMIntegrationEnums.eALMType, string> ALMSettingsFolders = new()
+    {
+        { GingerCoreNET.ALMLib.ALMIntegrationEnums.eALMType.Jira, "JiraSettings" },
+        { GingerCoreNET.ALMLib.ALMIntegrationEnums.eALMType.Qtest, "QTestSettings" }
+    };
+
     public static bool IsConfigPackageExists(string PackagePath, GingerCoreNET.ALMLib.ALMIntegrationEnums.eALMType eALMType)
     {
-        string settingsFolder = string.Empty;
-        settingsFolder = eALMType switch
-        {
-            GingerCoreNET.ALMLib.ALMIntegrationEnums.eALMType.Jira => "JiraSettings",
-            GingerCoreNET.ALMLib.ALMIntegrationEnums.eALMType.Qtest => "QTestSettings",
-            _ => "JiraSettings",
-        };
+        if (!ALMSettingsFolders.TryGetValue(eALMType, out string settingsFolder))
+        {
+            throw new ArgumentException($"Unsupported ALM type: {eALMType}", nameof(eALMType));
+        }
📝 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
string settingsFolder = string.Empty;
settingsFolder = eALMType switch
{
GingerCoreNET.ALMLib.ALMIntegrationEnums.eALMType.Jira => "JiraSettings",
GingerCoreNET.ALMLib.ALMIntegrationEnums.eALMType.Qtest => "QTestSettings",
_ => "JiraSettings",
};
private static readonly Dictionary<GingerCoreNET.ALMLib.ALMIntegrationEnums.eALMType, string> ALMSettingsFolders = new()
{
{ GingerCoreNET.ALMLib.ALMIntegrationEnums.eALMType.Jira, "JiraSettings" },
{ GingerCoreNET.ALMLib.ALMIntegrationEnums.eALMType.Qtest, "QTestSettings" }
};
if (!ALMSettingsFolders.TryGetValue(eALMType, out string settingsFolder))
{
throw new ArgumentException($"Unsupported ALM type: {eALMType}", nameof(eALMType));
}

if (Directory.Exists(Path.Combine(PackagePath, settingsFolder)))
{
return true;
}
else
{
Reporter.ToLog(eLogLevel.WARN, "Configuration package not exist in solution, Settings not exist at: " + Path.Combine(PackagePath, settingsFolder));
}
return false;
}
Comment on lines +660 to +678
Copy link
Contributor

Choose a reason for hiding this comment

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

⚠️ Potential issue

Add input validation and security checks.

The method should validate the input parameters to prevent potential issues:

  1. Path traversal vulnerability if PackagePath is not sanitized
  2. NullReferenceException if PackagePath is null

Consider applying this diff:

 public static bool IsConfigPackageExists(string PackagePath, GingerCoreNET.ALMLib.ALMIntegrationEnums.eALMType eALMType)
 {
+    if (string.IsNullOrEmpty(PackagePath))
+    {
+        Reporter.ToLog(eLogLevel.WARN, "PackagePath cannot be null or empty");
+        return false;
+    }
+
+    // Sanitize path to prevent path traversal
+    PackagePath = Path.GetFullPath(PackagePath);
+    if (!PackagePath.StartsWith(WorkSpace.Instance.Solution.Folder))
+    {
+        Reporter.ToLog(eLogLevel.WARN, $"PackagePath must be within solution folder: {PackagePath}");
+        return false;
+    }
+
     string settingsFolder = string.Empty;
     settingsFolder = eALMType switch
     {

Committable suggestion was skipped due to low confidence.

}

}
Expand Down
58 changes: 54 additions & 4 deletions Ginger/GingerCoreNET/GingerCoreNET.csproj
Original file line number Diff line number Diff line change
Expand Up @@ -54,7 +54,6 @@
<None Remove="DLLS\JiraRepositoryStd.dll" />
<None Remove="DLLS\LibGit2Sharp.dll" />
<None Remove="DLLS\OctaneInteractionStd.dll" />
<None Remove="DLLS\OctaneRepositoryStd.dll" />
<None Remove="DLLS\SikuliStandardNet.dll" />
<None Remove="DLLS\ZephyrEntStdSDK.dll" />
<None Remove="DLLS\Zepyhr_Ent_Repository_Std.dll" />
Expand Down Expand Up @@ -122,9 +121,6 @@
<Content Include="DLLS\OctaneInteractionStd.dll">
<CopyToOutputDirectory>PreserveNewest</CopyToOutputDirectory>
</Content>
<Content Include="DLLS\OctaneRepositoryStd.dll">
<CopyToOutputDirectory>PreserveNewest</CopyToOutputDirectory>
</Content>
<Content Include="DLLS\SikuliStandardNet.dll">
<CopyToOutputDirectory>PreserveNewest</CopyToOutputDirectory>
</Content>
Expand Down Expand Up @@ -361,13 +357,31 @@
<ItemGroup>
<Reference Include="ACL_Data_Contract">
<HintPath>DLLS\ACL_Data_Contract.dll</HintPath>
</Reference>
<Reference Include="ACL_Utils_Server">
<HintPath>DLLS\ACL_Utils_Server.dll</HintPath>
</Reference>
<Reference Include="AlmDataContractsStd">
<HintPath>DLLS\AlmDataContractsStd.dll</HintPath>
</Reference>
<Reference Include="ALMFactory">
<HintPath>DLLS\ALMFactory.dll</HintPath>
</Reference>
<Reference Include="AlmFactoryStd">
<HintPath>DLLS\AlmFactoryStd.dll</HintPath>
</Reference>
<Reference Include="ALMRepository">
<HintPath>DLLS\ALMRepository.dll</HintPath>
</Reference>
<Reference Include="AlmRepositoryStd">
<HintPath>DLLS\AlmRepositoryStd.dll</HintPath>
</Reference>
<Reference Include="ALMRestClient">
<HintPath>DLLS\ALMRestClient.dll</HintPath>
</Reference>
<Reference Include="ALMRestClientStd">
<HintPath>DLLS\ALMRestClientStd.dll</HintPath>
</Reference>
<Reference Include="ALM_CommonStd">
<HintPath>DLLS\ALM_CommonStd.dll</HintPath>
</Reference>
Expand All @@ -380,33 +394,69 @@
<Reference Include="GingerHbaseFilter">
<HintPath>DLLS\GingerHbaseFilter.dll</HintPath>
</Reference>
<Reference Include="Interop.TDAPIOLELib">
<HintPath>DLLS\Interop.TDAPIOLELib.dll</HintPath>
</Reference>
<Reference Include="JiraRepositoryStd">
<HintPath>DLLS\JiraRepositoryStd.dll</HintPath>
</Reference>
<Reference Include="LibGit2Sharp">
<HintPath>DLLS\LibGit2Sharp.dll</HintPath>
</Reference>
<Reference Include="ObjectsUtils">
<HintPath>DLLS\ObjectsUtils.dll</HintPath>
</Reference>
<Reference Include="OctaneRepositoryStd">
<HintPath>DLLS\OctaneRepositoryStd.dll</HintPath>
</Reference>
<Reference Include="OctaneSdkStandard">
<HintPath>DLLS\OctaneSdkStandard.dll</HintPath>
</Reference>
<Reference Include="OctaneStdSDK">
<HintPath>DLLS\OctaneStdSDK.dll</HintPath>
</Reference>
<Reference Include="Octane_Repository">
<HintPath>DLLS\Octane_Repository.dll</HintPath>
</Reference>
<Reference Include="protobuf-net">
<HintPath>DLLS\protobuf-net.dll</HintPath>
</Reference>
<Reference Include="QcRepository">
<HintPath>DLLS\QcRepository.dll</HintPath>
</Reference>
<Reference Include="QCRestClientStd">
<HintPath>DLLS\QCRestClientStd.dll</HintPath>
</Reference>
<Reference Include="QCRest_Repository">
<HintPath>DLLS\QCRest_Repository.dll</HintPath>
</Reference>
<Reference Include="QTestAPI">
<HintPath>DLLS\QTestAPI.dll</HintPath>
</Reference>
<Reference Include="QTestAPIStd">
<HintPath>DLLS\QTestAPIStd.dll</HintPath>
</Reference>
<Reference Include="QTestRepository">
<HintPath>DLLS\QTestRepository.dll</HintPath>
</Reference>
<Reference Include="RQMExport">
<HintPath>DLLS\RQMExport.dll</HintPath>
</Reference>
<Reference Include="RQMExportStd">
<HintPath>DLLS\RQMExportStd.dll</HintPath>
</Reference>
<Reference Include="RQM_Repository">
<HintPath>DLLS\RQM_Repository.dll</HintPath>
</Reference>
<Reference Include="RQM_RepositoryStd">
<HintPath>DLLS\RQM_RepositoryStd.dll</HintPath>
</Reference>
<Reference Include="SikuliStandardNet">
<HintPath>DLLS\SikuliStandardNet.dll</HintPath>
</Reference>
<Reference Include="SubAppUtils">
<HintPath>DLLS\SubAppUtils.dll</HintPath>
</Reference>
<Reference Include="ZephyrEntStdSDK">
<HintPath>DLLS\ZephyrEntStdSDK.dll</HintPath>
</Reference>
Expand Down
16 changes: 16 additions & 0 deletions Ginger/GingerRuntime/DotnetCoreHelper.cs
Original file line number Diff line number Diff line change
Expand Up @@ -290,6 +290,22 @@ private object UpdateALMType(eALMType almType)
case eALMType.Azure:
almCore = new AzureDevOpsCore();
break;
case eALMType.Qtest:
almCore = new QtestCore();
break;
case eALMType.QC:
if (CurrentAlmConfigurations.UseRest)
{
almCore = new QCRestAPICore();
}
else
{
almCore = new QCCore();
}
break;
case eALMType.RQM:
almCore = new RQMCore();
break;
Comment on lines +293 to +308
Copy link
Contributor

Choose a reason for hiding this comment

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

🛠️ Refactor suggestion

Consider implementing a factory pattern for ALM core instantiation.

The switch statement for ALM type handling is growing and could benefit from a more maintainable design pattern. Consider extracting this logic into a factory class to improve maintainability and testability.

Here's a suggested implementation:

public interface IALMCoreFactory
{
    ALMCore CreateALMCore(eALMType almType, ALMConfig config);
}

public class ALMCoreFactory : IALMCoreFactory
{
    public ALMCore CreateALMCore(eALMType almType, ALMConfig config)
    {
        if (config == null)
        {
            Reporter.ToLog(eLogLevel.ERROR, $"Missing configuration for {almType}");
            return null;
        }

        ALMCore core = almType switch
        {
            eALMType.Qtest => new QtestCore(),
            eALMType.QC when config.UseRest => new QCRestAPICore(),
            eALMType.QC => new QCCore(),
            eALMType.RQM => new RQMCore(),
            _ => null
        };

        if (core == null)
        {
            Reporter.ToLog(eLogLevel.ERROR, $"Failed to initialize {almType} core");
        }

        return core;
    }
}

Then update the UpdateALMType method:

-private object UpdateALMType(eALMType almType)
+private object UpdateALMType(eALMType almType, IALMCoreFactory factory = null)
 {
-    ALMCore almCore = null;
     ALMConfig CurrentAlmConfigurations = ALMCore.GetCurrentAlmConfig(almType);
     ALMCore.DefaultAlmConfig = CurrentAlmConfigurations;
-    //Set ALMRepo
-    switch (almType)
-    {
-        case eALMType.Qtest:
-            almCore = new QtestCore();
-            break;
-        // ... other cases
-    }
+    
+    factory ??= new ALMCoreFactory();
+    ALMCore almCore = factory.CreateALMCore(almType, CurrentAlmConfigurations);
     return almCore;
 }

⚠️ Potential issue

Ensure consistent error handling across ALM implementations.

The new ALM type implementations should follow the same error handling patterns as existing ones. A few observations:

  1. The Qtest and RQM cases don't verify the CurrentAlmConfigurations before instantiation, unlike the QC case.
  2. There's no null check on almCore after instantiation for any of the new cases.

Consider applying this more robust implementation:

 case eALMType.Qtest:
-    almCore = new QtestCore();
+    if (CurrentAlmConfigurations != null)
+    {
+        almCore = new QtestCore();
+        if (almCore == null)
+        {
+            Reporter.ToLog(eLogLevel.ERROR, $"Failed to initialize QtestCore");
+        }
+    }
+    else
+    {
+        Reporter.ToLog(eLogLevel.ERROR, $"Missing Qtest configuration");
+    }
     break;
 case eALMType.QC:
     if (CurrentAlmConfigurations.UseRest)
     {
         almCore = new QCRestAPICore();
+        if (almCore == null)
+        {
+            Reporter.ToLog(eLogLevel.ERROR, $"Failed to initialize QCRestAPICore");
+        }
     }
     else
     {
         almCore = new QCCore();
+        if (almCore == null)
+        {
+            Reporter.ToLog(eLogLevel.ERROR, $"Failed to initialize QCCore");
+        }
     }
     break;
 case eALMType.RQM:
-    almCore = new RQMCore();
+    if (CurrentAlmConfigurations != null)
+    {
+        almCore = new RQMCore();
+        if (almCore == null)
+        {
+            Reporter.ToLog(eLogLevel.ERROR, $"Failed to initialize RQMCore");
+        }
+    }
+    else
+    {
+        Reporter.ToLog(eLogLevel.ERROR, $"Missing RQM configuration");
+    }
     break;
📝 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
case eALMType.Qtest:
almCore = new QtestCore();
break;
case eALMType.QC:
if (CurrentAlmConfigurations.UseRest)
{
almCore = new QCRestAPICore();
}
else
{
almCore = new QCCore();
}
break;
case eALMType.RQM:
almCore = new RQMCore();
break;
case eALMType.Qtest:
if (CurrentAlmConfigurations != null)
{
almCore = new QtestCore();
if (almCore == null)
{
Reporter.ToLog(eLogLevel.ERROR, $"Failed to initialize QtestCore");
}
}
else
{
Reporter.ToLog(eLogLevel.ERROR, $"Missing Qtest configuration");
}
break;
case eALMType.QC:
if (CurrentAlmConfigurations.UseRest)
{
almCore = new QCRestAPICore();
if (almCore == null)
{
Reporter.ToLog(eLogLevel.ERROR, $"Failed to initialize QCRestAPICore");
}
}
else
{
almCore = new QCCore();
if (almCore == null)
{
Reporter.ToLog(eLogLevel.ERROR, $"Failed to initialize QCCore");
}
}
break;
case eALMType.RQM:
if (CurrentAlmConfigurations != null)
{
almCore = new RQMCore();
if (almCore == null)
{
Reporter.ToLog(eLogLevel.ERROR, $"Failed to initialize RQMCore");
}
}
else
{
Reporter.ToLog(eLogLevel.ERROR, $"Missing RQM configuration");
}
break;

default:
Reporter.ToLog(eLogLevel.ERROR, $"Invalid ALM Type - {almType}");
break;
Expand Down
Loading