30-01-24 02:47 PM
I am struggling to get the following query running as a Code query. The full query is -
using System;
using System.Net.Http;
using System.Threading.Tasks;
using Newtonsoft.Json.Linq;
class Program
{
static async Task Main()
{
DateTime currentDate = DateTime.Now;
DateTime firstDayOfMonth = new DateTime(currentDate.Year, currentDate.Month, 1);
// Check if the current day is a working day (Monday to Friday),
// is the first day of the month, and is not a bank holiday
if (currentDate.DayOfWeek >= DayOfWeek.Monday &&
currentDate.DayOfWeek <= DayOfWeek.Friday &&
currentDate.Date == firstDayOfMonth &&
!await IsBankHoliday(currentDate))
{
// It is the first working day of the month
Console.WriteLine("It is the first working day of the month");
}
else
{
// It is not the first working day of the month
Console.WriteLine("It is not the first working day of the month");
}
}
static async Task<bool> IsBankHoliday(DateTime checkDate)
{
using (HttpClient client = new HttpClient())
{
try
{
// Make an HTTP request to get bank holidays JSON
string json = await client.GetStringAsync("https://www.gov.uk/bank-holidays.json");
// Parse JSON response
JObject bankHolidayData = JObject.Parse(json);
// Extract bank holidays for England and Wales
JArray bankHolidays = (JArray)bankHolidayData["england-and-wales"]["events"];
// Check if the checkDate is in the list of bank holidays
foreach (JToken holiday in bankHolidays)
{
if (DateTime.Parse(holiday["date"].ToString()).Date == checkDate.Date)
{
return true;
}
}
return false;
}
catch (HttpRequestException)
{
// Handle request exception, e.g., if the URL is unreachable
Console.WriteLine("Error: Unable to retrieve bank holidays data.");
return false;
}
catch (Exception ex)
{
// Handle other exceptions
Console.WriteLine($"Error: {ex.Message}");
return false;
}
}
}
}
It doesn't seem to matter if I add the code to Global or a Code Object, I get the error - Compiler Error at top section line 98: Type or namespace definition, or end-of-file expected.
I have added in the External References for Newtonsoft.Json.dll, System.Net.Http.dll & System.Threading.Tasks.Extensions.dll.
I have set namespaces up for System.Threading.Tasks, System.Net.Http.HttpClient & Newtonsoft.Json.Linq.
I'm sure I'm missing something simple but I can't for the life of me see what, any help would be appreciated.
Many Thanks
30-01-24 11:33 PM
Hello Neil,
Try doing this way. No need for 'using' declarations in your code. Instead, consider configuring external references and namespace imports in the code options.
Let me know if that works for you.
public class GlobalCode
{
// Class Variables
private static string output;
private static string errorMessage;
public static string Main()
{
DateTime currentDate = DateTime.Now;
DateTime firstDayOfMonth = new DateTime(currentDate.Year, currentDate.Month, 1);
// Check if the current day is a working day (Monday to Friday),
// is the first day of the month, and is not a bank holiday
if (currentDate.DayOfWeek >= DayOfWeek.Monday &&
currentDate.DayOfWeek <= DayOfWeek.Friday &&
currentDate.Date == firstDayOfMonth &&
!IsBankHolidayAsync(currentDate).Result) // Use .Result to synchronously wait for the task
{
// It is the first working day of the month
output = "It is the first working day of the month";
}
else
{
// It is not the first working day of the month
output = "It is not the first working day of the month";
}
return output; // Return the result
}
public static async Task<bool> IsBankHolidayAsync(DateTime checkDate)
{
return await Task.Run(async () =>
{
using (HttpClient client = new HttpClient())
{
try
{
// Make an HTTP request to get bank holidays JSON
string json = await client.GetStringAsync("https://www.gov.uk/bank-holidays.json");
// Parse JSON response
JObject bankHolidayData = JObject.Parse(json);
// Extract bank holidays for England and Wales
JArray bankHolidays = (JArray)bankHolidayData["england-and-wales"]["events"];
// Check if the checkDate is in the list of bank holidays
foreach (JToken holiday in bankHolidays)
{
if (DateTime.Parse(holiday["date"].ToString()).Date == checkDate.Date)
{
return true;
}
}
return false;
}
catch (HttpRequestException)
{
// Handle request exception, e.g., if the URL is unreachable
errorMessage = "Error: Unable to retrieve bank holidays data.";
return false;
}
catch (Exception ex)
{
// Handle other exceptions
errorMessage = $"Error: {ex.Message}";
return false;
}
}
});
}
}
30-01-24 11:41 PM
In simple terms, code stages/global code in BP are not console apps, so Main method has no place in BP...
In summary:
1) The global code of a BP Object is the body of a class
2) A code stage gets transformed to the body of a method of that class (spaces in the code stage name are auto-replaced by "_")
Use the global code or code stages as methods to return values to a calling process page.
Only Object pages can be seen by a process, but Object pages may call code from Global code as per preferred design.
I'd set up an action (object page with code stage) that returns a Flag (boolean)
31-01-24 08:01 AM
Thank you so much for your help with this! Was my first time using code in BP and I just couldn't see where it was going wrong, your solution made perfect sense and worked exactly as needed.