Is there a better way to combine if statement with an ISR?
Your code is not blocked, but ON or OFF are called each loop so your change are to the "common" components are overwritten quite fast.

Do not track the state within the IRQ. You could do something like:

volatile byte alarm = 1;
byte alarm_state = 1;

void ISR_Alarm () {
    alarm = 1;  
}

void loop() {
    if (alarm){
        alarm = 0;

        if (alarm_state) {
            alarm_state = 0;
            alarm_Off();
        } else {
            alarm_state = 1;
            alarm_On();
        }
    }

    // other code
}