Calculation of IRR

Hi!
I try to calculate IRR for a bond with
start date: 2022-01-03
maturity date: 2025-01-03
settlement date: 2022-11-04
coupon: 2% (annual)
frequency: semiannual (Frequency.P6M)
day count: act/365 (DayCounts.ACT_365L)
clean price: 97

Using yieldFromDirtyPrice, I’ve a irr of 0.0345149172.
Using MS XIRR I’ve a irr of 0.0347078830.

Discounting cashflow with MS XIRR I got, exactly, the dirty price (97.6794520548),
Using strata irr I got 97.7180266080.

this is my code

public static void test() {
LocalDate settlementDate = LocalDate.of(2022,11, 4);
LocalDate startDate = LocalDate.of(2022,1, 3);
LocalDate maturityDate = LocalDate.of(2025,1, 3);
double couponRate = 0.02;

    BusinessDayAdjustment businessDayAdj = BusinessDayAdjustment.of(
            BusinessDayConventions.NO_ADJUST, HolidayCalendarIds.NO_HOLIDAYS);

    PeriodicSchedule accrualSchedule = PeriodicSchedule
            .builder()
            .startDate(startDate)
            .endDate(maturityDate)
            .lastRegularEndDate(maturityDate)
            .businessDayAdjustment(businessDayAdj)
            .frequency(Frequency.P6M)
            .stubConvention(StubConvention.NONE)
            .rollConvention(RollConventions.EOM)
            .build();

    FixedCouponBond fcb = FixedCouponBond
            .builder()
            .accrualSchedule(accrualSchedule)
            .currency(Currency.EUR)
            .securityId(SecurityId.of("CUSIP", "135087WL4"))
            .notional(100.)
            .fixedRate(couponRate)
            .dayCount(DayCounts.ACT_365L)
            .yieldConvention(FixedCouponBondYieldConvention.DE_BONDS)
            .legalEntityId(LegalEntityId.of("LegalEntity", "DUMMY"))
            .settlementDateOffset(DaysAdjustment.ofBusinessDays(3, HolidayCalendarIds.CATO))
            .build();

    ResolvedFixedCouponBond resolvedBond = fcb.resolve(ReferenceData.standard());
    double cleanPrice = 97 / 100.;
    double dirtyPrice = DiscountingFixedCouponBondProductPricer.DEFAULT.dirtyPriceFromCleanPrice(resolvedBond, settlementDate,cleanPrice);
    double accrual = DiscountingFixedCouponBondProductPricer.DEFAULT.accruedInterest(resolvedBond, settlementDate);
    double yield = DiscountingFixedCouponBondProductPricer.DEFAULT.yieldFromDirtyPrice(resolvedBond, settlementDate, dirtyPrice);
    double calculatedDirty = DiscountingFixedCouponBondProductPricer.DEFAULT.dirtyPriceFromYield(resolvedBond, settlementDate, yield);
    double macaulayDuration = DiscountingFixedCouponBondProductPricer.DEFAULT.macaulayDurationFromYield(resolvedBond, settlementDate, yield);
    double modifiedDuration = DiscountingFixedCouponBondProductPricer.DEFAULT.modifiedDurationFromYield(resolvedBond, settlementDate, yield);

    System.out.println("yield: " + yield);
    System.out.println("dirty: " + dirtyPrice);
    System.out.println("calculatedDirty: " + calculatedDirty);
    System.out.println("macaulayDuration: " + macaulayDuration);
    System.out.println("modifiedDuration: " + modifiedDuration);
    System.out.println("accrual: " + accrual);
    System.out.println("accrual days: " + DiscountingFixedCouponBondProductPricer.DEFAULT.accruedYearFraction(resolvedBond, settlementDate) * 365.);

}

What it’s wrong?