asp.netasp.net-coredatedatetimeweek-number

How to get previous/next week number and year in ASP.NET Core 6


I have this Week based navigation in the UI and on click on the left/right arrows I was calling an API and returning the data with previous week/year number and next week/year number but now I need to handle it in ASP.NET Core 6. So it was working fine using PHP with API. The PHP code is given below with request and output.

enter image description here

The below code of PHP is working as expected. But I need same output in APS.NET Core 6.

$prev_week = date ("W", strtotime ($year. 'W' . $week . ' -1 week'));
$prev_year = date ("o", strtotime ($year. 'W' . $week . ' -1 week'));
$next_week = date ("W", strtotime ($year. 'W' . $week . ' +1 week'));
$next_year = date ("o", strtotime ($year. 'W' . $week . ' +1 week'));

If I have week as 52 and Year 2023 then the output of this code will be :

prev_week 51
prev_year 2023
next_week 01
next_year 2024

Now I am trying to convert the above code into ASP.NET Core 6 but I am not able to get the exact output as PHP. Here is what I did till now.

As I have already Year and Week number so I just wanted to get the previous and Next week and if its year end or first week of year then the previous week and year should say week as 1 and Year should be previous year.

using System;

int prev_week = DateTime.ParseExact($"{year}-W{week}", "yyyy-'W'w", null).AddWeeks(-1).Week;
int prev_year = DateTime.ParseExact($"{year}-W{week}", "yyyy-'W'w", null).AddWeeks(-1).Year;
int next_week = DateTime.ParseExact($"{year}-W{week}", "yyyy-'W'w", null).AddWeeks(1).Week;
int next_year = DateTime.ParseExact($"{year}-W{week}", "yyyy-'W'w", null).AddWeeks(1).Year;

this code is not giving me same result.

I would like to get the same output as shown above as getting from php using viewmodel in asp.net core 6 web api.


Solution

  • I suggest you could use nodatime package and try to use below codes:

    You could install by using below nuget package command.

    Install-Package NodaTime

    You could create a model class:

    public class WeekYearInfo
    {
        public int PrevWeek { get; set; }
        public int PrevYear { get; set; }
        public int NextWeek { get; set; }
        public int NextYear { get; set; }
    }
    

    Then you could create a calculate method:

        public static WeekYearInfo CalculatePrevNextWeekYear(int year, int week)
       {
           LocalDate inputDate = LocalDate.FromWeekYearWeekAndDay(year, week, IsoDayOfWeek.Monday);
           LocalDate prevWeekDate = inputDate.PlusWeeks(-1);
           LocalDate nextWeekDate = inputDate.PlusWeeks(1);
           IWeekYearRule rule = WeekYearRules.Iso;
    
           return new WeekYearInfo
           {
               PrevWeek = rule.GetWeekOfWeekYear(prevWeekDate),
               PrevYear = rule.GetWeekYear(prevWeekDate),
               NextWeek = rule.GetWeekOfWeekYear(nextWeekDate),
               NextYear = rule.GetWeekYear(nextWeekDate)
           };
       }
    

    At last, you could call it inside the controller:

        public IActionResult Privacy()
        {
            int year = 2023;
            int week = 52;
            WeekYearInfo result = CalculatePrevNextWeekYear(year, week);
    
            return View(result);
        }
    

    Result:

    enter image description here


    Edit:

        public static WeekYearInfo CalculatePrevNextWeekYear(int year, int week)
        {
    
    
            DateTime firstDayOfYear = new DateTime(year, 1, 1);
            int daysOffset = DayOfWeek.Thursday - firstDayOfYear.DayOfWeek;
            DateTime firstThursday = firstDayOfYear.AddDays(daysOffset);
            var cal = CultureInfo.CurrentCulture.Calendar;
            int firstWeek = cal.GetWeekOfYear(firstThursday, CalendarWeekRule.FirstFourDayWeek, DayOfWeek.Monday);
    
            DateTime targetDate = firstDayOfYear.AddDays(week * 7 - (firstWeek == 1 ? 0 : 7));
            DateTime prevWeekDate = firstDayOfYear.AddDays(-7);
            DateTime nextWeekDate = firstDayOfYear.AddDays(7);
    
            return new WeekYearInfo
            {
                PrevWeek = cal.GetWeekOfYear(prevWeekDate, CalendarWeekRule.FirstFourDayWeek, DayOfWeek.Monday),
                PrevYear = prevWeekDate.Year,
                NextWeek = cal.GetWeekOfYear(nextWeekDate, CalendarWeekRule.FirstFourDayWeek, DayOfWeek.Monday),
                NextYear = nextWeekDate.Year
            };
        }