Problem polega na tym, że jestem prawie pewien, że nie można sprawdzić, czy CSS jest skutecznie dodawany do strony przez PHP: CSS jest analizowany przez przeglądarkę, więc po stronie klienta i nie ma żadnego wpływu na stronę serwera.
Oczywiście w PHP można sprawdzić, czy CDN reaguje, czy nie ...
opcja 1
Wyślij żądanie, a jeśli odpowie ono statusem HTTP 200, użyj go. Coś jak:
function font_awesome_css() {
$url = 'http://netdna.bootstrapcdn.com/font-awesome/4.0.3/css/font-awesome.min.css';
$cdn = wp_remote_get( $url );
if ( (int) wp_remote_retrieve_response_code( $cdn) !== 200 ) {
$url = get_template_directory_uri() . '/css/font-awesome/css/font-awesome.min.css';
}
wp_enqueue_style( 'font-awesome', $url, false );
}
co powoduje 2 żądania HTTP, jedno do sprawdzenia, drugie do wbudowanego CSS: naprawdę źle .
Opcja 2
function font_awesome_css() {
$url = 'http://netdna.bootstrapcdn.com/font-awesome/4.0.3/css/font-awesome.min.css';
$cdn = wp_remote_get( $url );
if ( (int) wp_remote_retrieve_response_code( $cdn ) === 200 ) {
$css = wp_remote_retrieve_body( $cdn );
add_action( 'wp_head', function() use( $css ) {
$absolute = "//netdna.bootstrapcdn.com/font-awesome/4.0.3/fonts/";
$css = str_replace( "../fonts/", $absolute, $css );
echo '<style type="text/css">' . $css . '</style>';
} );
} else {
$url = get_template_directory_uri() . '/css/font-awesome/css/font-awesome.min.css';
wp_enqueue_style( 'font-awesome', $url, false );
}
}
Jest jeszcze gorzej :
- Rujnuje
wp_enqueue_style
przepływ pracy: jeśli wtyczka doda czcionkę Awesome, zostanie dodana 2 razy.
- Liczba żądań HTTP jest taka sama, jednak zwykle 2 żądania działają równolegle , więc w ten sposób generowanie strony PHP spowalnia, ponieważ musi czekać na odpowiedź na pierwsze żądanie.
- Zapobiega to również buforowaniu CSS przez przeglądarkę, więc jeśli używasz tego samego stylu na różnych stronach, wymuszasz żądanie CDN na każdej odwiedzanej stronie. Podczas korzystania z normalnego przepływu pracy strony po pierwszym CSS są pobierane z pamięci podręcznej.
Tak naprawdę nie rób tego w domu.
Ważne jest to, że za pomocą PHP można sprawdzić żądanie CDN, ale nie weryfikować CSS, więc wszystkie twoje wysiłki kończą się gorszą wydajnością, a nie lepszą.
Z poważaniem, jeśli twój jest motywem publicznym, sugeruję, abyś używał tylko kopii lokalnej, umożliwiając użytkownikom wybór CDN:
if ( ! function_exists( 'font_awesome_css' ) ) {
function font_awesome_css() {
$_url = get_template_directory_uri() . '/css/font-awesome/css/font-awesome.min.css';
$url = apply_filters( 'font_awesome_css_url', $_url );
wp_enqueue_style( 'font-awesome', $url, false );
}
}
Dzięki temu użytkownicy mogą całkowicie zastąpić tę funkcję za pomocą motywu podrzędnego, a także mogą użyć 'font_awesome css_url'
filtra do zmiany adresu URL.
Weź również pod uwagę, że niektórzy wysokiej klasy dostawcy hostingu automatycznie przekształcają zasoby lokalne na CDN, a istnieją wtyczki, które pozwalają CDN na wszystkie te rzeczy; jest to powód, dla którego motyw publiczny nie powinien w ogóle używać CDN.
Jeśli motyw jest dla Ciebie, dokonaj wyboru. Weź pod uwagę, że najbardziej znane sieci CDN mają bardzo niski procent przestojów (a bootstrapcdn jest jednym z najbardziej niezawodnych, według cdnperf.com ). Jestem prawie pewien, że twój hosting ma% przestoju większy niż bootstrapcdn, więc ludzie mają większe prawdopodobieństwo, że w ogóle nie zobaczą twojej witryny, niż zepsutymi ikonami.
Brudna droga
Jak już powiedziano, PHP nie może sprawdzić CSS, ponieważ renderowanie CSS odbywa się po stronie klienta, ale można użyć sprawdzania po stronie klienta: JavaScript.
Najpierw umieść CSS za pomocą CDN:
function font_awesome_css() {
$url = '//netdna.bootstrapcdn.com/font-awesome/4.0.3/css/font-awesome.min.css';
wp_enqueue_style( 'font-awesome', $url, false );
}
Następnie dodaj stopkę JavaScript do stopki:
/*
Normally the JS should be properly enqueued and the URL
passed via wp_enqueue_script, but this is a proof of concept,
more than real code.
*/
add_action( 'wp_footer', function() {
$cssurl = get_template_directory_uri() . '/css/';
?>
<span id="facheck" data-cssuri="<?php echo $cssurl; ?>" class="fa" style="display:none">
</span>
<script>
jQuery(document).ready(function($) {
var $check = $('#facheck');
if ( $check.css('fontFamily') !== 'FontAwesome' ) {
// Font Awesome not loaded!
// Remove current CSS link
$('#font-awesome-css').remove;
// Add the local version
var local = '<link rel="stylesheet" type="text/css" href="' +
$check.data('cssuri') + // This is the theme CSS folder URL
'font-awesome/css/font-awesome.min.css" />';
$('head').append( local );
}
});
</script>
<?php
});
Ten kod jest uruchamiany podczas ładowania strony i sprawdza, czy niewidoczny zakres dodany do stopki w klasie „fa” ma właściwość font-family ustawioną na „FontAwesome”. Jest to ustawiane przez Font Awesome, więc jeśli to nieprawda, oznacza to, że CSS nie jest ładowany. Jeśli tak się stanie, kod używa JavaScript, aby dołączyć lokalny CSS do nagłówka.
(Aby przetestować ten kod, możesz osadzić za wp_enqueue_style
pomocą niewłaściwego adresu URL CDN i zobaczyć, co się stanie)
Dlatego w rzadkim przypadku, gdy CDN nie jest dostępny, wszystkie style będą wyświetlane zgodnie z oczekiwaniami (przez kilka milisekund użytkownicy zobaczą „zepsute” ikony CSS, ponieważ CSS jest dodawany po załadowaniu strony).
Teraz, biorąc pod uwagę, że CDN są bardzo niezawodne, czy warto wykonać ten hack dla <1% osób, które zobaczą zepsute ikony? Odpowiedź na to pytanie należy do Ciebie.
is_readable($cdnPath)
?