Wymuś dystrybucję / aktualizację plików CloudFront

146

Używam CloudFront firmy Amazon do obsługi plików statycznych moich aplikacji internetowych.

Czy nie ma sposobu, aby powiedzieć dystrybucji Cloudfront, że musi odświeżyć swój plik lub wskazać pojedynczy plik, który powinien zostać odświeżony?

Amazon zaleca wersjonowanie plików, takich jak logo_1.gif, logo_2.gif i tak dalej jako obejście tego problemu, ale wydaje się to dość głupim rozwiązaniem. Czy nie ma innego wyjścia?

Jaskółka oknówka
źródło
na marginesie, nie sądzę, aby nazywanie plików statycznych w ten sposób było głupie. Używaliśmy go dużo, a automatyczna zmiana nazwy zgodnie z wersją pliku w kontroli wersji zaoszczędziła nam wielu bólów głowy.
eis
1
@eis, chyba że plik, który chcesz zastąpić, został powiązany z 1000 różnych miejsc online. Powodzenia w aktualizowaniu wszystkich tych linków.
Jake Wilson
@Jakobud dlaczego w takim przypadku linki powinny zostać zaktualizowane? odnoszą się do konkretnej wersji, która nie jest najnowsza, jeśli plik został zmieniony. Jeśli plik nie został zmieniony, będzie działać tak, jak wcześniej.
eis
6
W niektórych przypadkach firma może popełnić błąd, publikując niewłaściwy obraz dla czegoś lub innego rodzaju przedmiotu, w przypadku gdy otrzyma od firmy prawniczej żądanie usunięcia i będzie musiała wymienić plik. Samo przesłanie nowego pliku z nową nazwą nie rozwiąże tego rodzaju problemu, który niestety jest obecnie coraz bardziej powszechny.
Jake Wilson

Odpowiedzi:

134

Dobre wieści. Amazon w końcu dodał funkcję unieważnienia. Zobacz dokumentację API .

Oto przykładowe żądanie z dokumentacji API:

POST /2010-08-01/distribution/[distribution ID]/invalidation HTTP/1.0
Host: cloudfront.amazonaws.com
Authorization: [AWS authentication string]
Content-Type: text/xml

<InvalidationBatch>
   <Path>/image1.jpg</Path>
   <Path>/image2.jpg</Path>
   <Path>/videos/movie.flv</Path>
   <CallerReference>my-batch</CallerReference>
</InvalidationBatch>
James Lawruk
źródło
9
Pamiętaj, że unieważnienie zajmie trochę czasu (podobno 5-30 minut według niektórych postów na blogu, które przeczytałem).
Michael Warkentin
37
Jeśli nie chcesz samodzielnie wysyłać żądania API, możesz również zalogować się do Amazon Console i tam utworzyć żądanie unieważnienia
j0nes
Dla tych z Was, którzy używają interfejsu API do unieważniania, w przybliżeniu ile czasu potrzeba, aby unieważnienie zaczęło obowiązywać?
ill_always_be_a_warriors
20
Pamiętaj, że po 1000 pierwszych żądań unieważnienia miesięcznie kosztuje to 0,005 USD aws.amazon.com/cloudfront/pricing
TimS
1
@MichaelWarkentin Po wysłaniu createInvalidationżądania API nadal widzę, że aktualizacja zajmuje około 5-10 minut, aby unieważnić. Zauważ, że piszę ten komentarz 4 lata po twoim.
tim Peterson
19

Od 19 marca Amazon zezwala teraz na TTL pamięci podręcznej Cloudfront na 0 sekund, więc (teoretycznie) nigdy nie powinieneś widzieć nieaktualnych obiektów. Jeśli więc masz swoje zasoby w S3, możesz po prostu przejść do AWS Web Panel => S3 => Edytuj właściwości => Metadane, a następnie ustawić wartość „Cache-Control” na „max-age = 0”.

To prosto z dokumentacji API :

Aby kontrolować, czy CloudFront buforuje obiekt i jak długo, zalecamy użycie nagłówka Cache-Control z dyrektywą max-age =. CloudFront buforuje obiekt przez określoną liczbę sekund. (Minimalna wartość to 0 sekund.)

John K. Chow
źródło
Gdzie jest to ustawienie w nowym interfejsie użytkownika konsoli AWS? Nie mogę tego znaleźć.
ill_always_be_a_warriors
1
Znalazłem ustawienie dla pojedynczego pliku, ale czy istnieje takie ustawienie, aby wszystko przesłane do mojego zasobnika miało TTL równe 0?
ill_always_be_a_warriors
Chociaż na pewno byłbym zainteresowany ustawieniem obejmującym całe wiadro, uznałem to za szybsze / lepsze rozwiązanie. Żądania unieważnienia (wraz z resztą API) są bardzo zagmatwane i słabo udokumentowane, więc obracałem kołami przez 3 godziny, zanim to natychmiast zadziałało.
Two-Bit Alchemist
33
Nazwij mnie szalonym, ale ustawienie TTL na 0 i max-age na 0 naprawdę używa CloudFront bez buforowania, czy nie byłoby to przekazywanie wszystkich żądań do źródła ciągłego sprawdzania dostępności aktualizacji? Zasadniczo czyniąc CDN bezużytecznym?
acidjazz
6
Jeśli używasz tylko chmury jako mechanizmu do posiadania statycznej witryny S3 z obsługą SSL i domeną niestandardową, buforowanie nie ma znaczenia. Ponadto omawiamy te kwestie, że w fazach rozwoju buforowanie zerowe jest dobre.
Dan G
10

Dzięki interfejsowi Invalidation API jest aktualizowany w ciągu kilku minut.
Sprawdź PHP Invalidator .

anjanesh
źródło
To jest dokładnie to, czego szukałem. Zamierzam to podpiąć do web-hooków Beanstalkapp podczas automatycznego wdrażania z git! Dzięki za link!
cointilt
10

Automatyczna konfiguracja aktualizacji w 5 minut

W porzadku chlopaki. Na razie najlepszym możliwym sposobem wykonania automatycznej aktualizacji CloudFront (unieważnienia) jest utworzenie funkcji Lambda, która będzie uruchamiana za każdym razem, gdy jakikolwiek plik zostanie załadowany do wiadra S3 (nowy lub przepisany).

Nawet jeśli nigdy wcześniej nie korzystałeś z funkcji lambda, jest to naprawdę łatwe - postępuj zgodnie z moimi instrukcjami krok po kroku, a zajmie to tylko 5 minut:

Krok 1

Wejdź na https://console.aws.amazon.com/lambda/home i kliknij Utwórz funkcję lambda

Krok 2

Kliknij opcję Pusta funkcja (niestandardowa)

Krok 3

Kliknij puste (obrysowane) pole i wybierz S3 z combo

Krok 4

Wybierz swój Bucket (tak samo jak w przypadku dystrybucji CloudFront)

Krok 5

Ustaw Typ zdarzenia na „Utworzono obiekt (wszystkie)”

Krok 6

Ustaw prefiks i sufiks lub pozostaw je puste, jeśli nie wiesz, co to jest.

Krok 7

Zaznacz pole wyboru Włącz wyzwalacz i kliknij Dalej

Krok 8

Nazwij swoją funkcję (na przykład: YourBucketNameS3ToCloudFrontOnCreateAll )

Krok 9

Wybierz Python 2.7 (lub nowszy) jako Runtime

Krok 10

Wklej następujący kod zamiast domyślnego kodu Pythona:

from __future__ import print_function

import boto3
import time

def lambda_handler(event, context):
    for items in event["Records"]:
        path = "/" + items["s3"]["object"]["key"]
        print(path)
        client = boto3.client('cloudfront')
        invalidation = client.create_invalidation(DistributionId='_YOUR_DISTRIBUTION_ID_',
            InvalidationBatch={
            'Paths': {
            'Quantity': 1,
            'Items': [path]
            },
            'CallerReference': str(time.time())
            })

Krok 11

Otwórz https://console.aws.amazon.com/cloudfront/home w nowej karcie przeglądarki i skopiuj swój identyfikator dystrybucji CloudFront do wykorzystania w następnym kroku.

Krok 12

Wróć do zakładki lambda i wklej swój identyfikator dystrybucji zamiast _YOUR_DISTRIBUTION_ID_ w kodzie Pythona. Zachowaj otaczające cytaty.

Krok 13

Ustaw obsługę : lambda_function.lambda_handler

Krok 14

Kliknij pole wyboru ról i wybierz opcję Utwórz rolę niestandardową . Otworzy się nowa karta w przeglądarce.

Krok 15

Kliknij wyświetl dokument zasad , kliknij edytuj , kliknij OK i zastąp definicję roli następującą (taką jaka jest):

{
  "Version": "2012-10-17",
  "Statement": [
    {
      "Effect": "Allow",
      "Action": [
        "logs:CreateLogGroup",
        "logs:CreateLogStream",
        "logs:PutLogEvents"
      ],
      "Resource": "arn:aws:logs:*:*:*"
    },
    {
      "Effect": "Allow",
      "Action": [
          "cloudfront:CreateInvalidation"
      ],
      "Resource": [
          "*"
      ]
    }
  ]
}

Krok 16

Kliknij Zezwól . Spowoduje to powrót do lambda. Dokładnie sprawdź, czy nazwa roli, którą właśnie utworzyłeś, jest wybrana w polu kombinacji Istniejąca rola .

Krok 17

Ustaw pamięć (MB) na 128 i limit czasu na 5 sek.

Krok 18

Kliknij przycisk Dalej , a następnie kliknij opcję Utwórz funkcję

Krok 19

Możesz ruszać! Teraz za każdym razem, gdy prześlesz / ponownie załadujesz dowolny plik do S3, zostanie on oceniony we wszystkich lokalizacjach CloudFront Edge.

PS - Podczas testowania upewnij się, że Twoja przeglądarka ładuje obrazy z CloudFront, a nie z lokalnej pamięci podręcznej.

PSS - Należy pamiętać, że tylko pierwsze unieważnienie 1000 plików miesięcznie jest bezpłatne, a każde unieważnienie powyżej limitu kosztuje 0,005 USD. Mogą obowiązywać dodatkowe opłaty za funkcję Lambda, ale jest ona wyjątkowo tania.

Kainax
źródło
Tylko ostatnia pozycja z każdej partii S3?
Phil
@Phil Kod jest napisany w ten sposób, więc tylko nowo przesłane pliki zostaną unieważnione, a nie cały zasobnik. W przypadku przesłania wielu plików każdy z nich zostanie oddzielnie unieważniony. Działa jak marzenie.
Kainax,
Jedynym powodem, dla którego ten kod działa zgodnie z oczekiwaniami, jest to, że S3 obecnie zawiera tylko jeden element na powiadomienie, tj.Długość tablicy na szczęście zawsze wynosi 1, a co za tym idzie, nawet jeśli załadujesz wiele plików za jednym razem, otrzymasz zupełnie nowe powiadomienie na plik. W żadnym wypadku nie otrzymasz powiadomienia dla całego segmentu. Niemniej jednak napisany kod nie jest gotowy na zmianę tego zachowania przez AWS. O wiele bezpieczniej jest pisać kod, który obsługuje całą tablicę, niezależnie od długości, co było moim pierwotnym (niestety przeoczonym) punktem.
Phil,
Jedynym powodem, dla którego AWS dodaje moduły obsługi zdarzeń, jest ... cóż ... obsługa zdarzeń. Dlaczego mieliby to usunąć? Bez względu na to, w jaki sposób nowy plik został dodany, powinien wyzwolić zdarzenie dla API i tak to teraz działa i będzie nadal działać. Używam AWS od 4 lat i nigdy niczego nie zmienili, więc poprzedni kod przestał działać. Nawet jeśli zmieniają API, zmieniają go na nową, samodzielną wersję, ale wszystkie poprzednie wersje są zawsze obsługiwane. W tym konkretnym przypadku po prostu nie wierzę, że zdarzenie w pliku osobistym kiedykolwiek zostanie usunięte. Prawdopodobnie jest już używany przez miliony projektów na całym świecie.
Kainax,
W przypadku, gdy źle zrozumiem Twój pierwszy komentarz i masz na myśli, że „Ilość”: 1 doda tylko ostatnią pozycję - dla każdego elementu tablicy jest pętla FOR.
Kainax
9

Bucket Explorer ma interfejs użytkownika, który teraz czyni to całkiem prostym. Oto jak:

Kliknij prawym przyciskiem myszy swoje wiadro. Wybierz „Zarządzaj dystrybucjami”.
Kliknij prawym przyciskiem myszy swoją dystrybucję. Wybierz „Pobierz listę unieważnień Cloudfront”, a następnie wybierz „Utwórz”, aby utworzyć nową listę unieważnień. Wybierz pliki do unieważnienia i kliknij „Unieważnij”. Poczekaj 5-15 minut.

Leopd
źródło
4

Jeśli masz zainstalowany boto (który jest nie tylko dla Pythona, ale także instaluje kilka przydatnych narzędzi wiersza poleceń), oferuje narzędzie wiersza poleceń o nazwie cfadminlub `` administrator frontowy chmury '', które oferuje następujące funkcje:

Usage: cfadmin [command]
cmd - Print help message, optionally about a specific function
help - Print help message, optionally about a specific function
invalidate - Create a cloudfront invalidation request
ls - List all distributions and streaming distributions

Unieważniasz rzeczy, biegając:

$sam# cfadmin invalidate <distribution> <path>
samurajsam
źródło
W rzeczywistości cfadmin jest bardzo pomocnym narzędziem, zwłaszcza jeśli chcesz zresetować pamięć podręczną CloudFront z poziomu skryptu wdrażania konsoli \ bash \ travis ci. BTW tutaj jest post jak zresetować \ unieważnić pamięć podręczną CoudFront podczas wdrażania travisa do aws
Mikita Manko
3

Po prostu wysyłam wiadomość, aby poinformować każdego odwiedzającego tę stronę (pierwszy wynik w `` Odświeżaniu plików w chmurze ''), że istnieje łatwy w użyciu + dostęp online unieważniacz dostępny na swook.net

Ten nowy umniejszacz to:

  • W pełni online (bez instalacji)
  • Dostępny 24x7 (hostowany przez Google) i nie wymaga członkostwa.
  • Dostępna jest obsługa historii i sprawdzanie ścieżek, które pozwalają z łatwością unieważniać pliki. (Często wystarczy kilka kliknięć po pierwszym unieważnieniu!)
  • Jest również bardzo bezpieczny, o czym przekonasz się czytając jego publikację .

Pełne ujawnienie: zrobiłem to. Baw się dobrze!

swook
źródło
2
przepraszam, ale nawet „mówisz”, że dane uwierzytelniające nie zostały zapisane lub przetrzymane ... nigdy nie należy ich podawać osobom trzecim. Może zaimplementować zdalne uwierzytelnianie Amazon czy coś?
d.raev
Powinieneś umieścić to przynajmniej za https.
Oliver Tynes
Narzędzia online są ogólnie przyjemne, ale podanie danych uwierzytelniających do narzędzia innej firmy będzie ważnym problemem bezpieczeństwa. Sugerowałbym użycie oficjalnej konsoli internetowej lub oficjalnego narzędzia CLI .
RayLuo
2
Ze względu na bezpieczeństwo innych odrzucam tę odpowiedź. Nigdy nie powinieneś pytać ludzi o ich referencje
Moataz Elmasry
3

bardzo prostym sposobem jest przechowywanie wersji FOLDERÓW.

Więc jeśli na przykład twoje pliki statyczne są setki, po prostu umieść je wszystkie w folderze o nazwie rok + wersjonowanie.

na przykład używam folderu o nazwie 2014_v1, w którym mam wszystkie moje pliki statyczne ...

Dlatego w moim kodzie HTML zawsze umieszczam odniesienie do folderu. (oczywiście mam PHP, w którym ustawiłem nazwę folderu.) Więc zmieniając w 1 pliku, zmienia się to we wszystkich moich plikach PHP ..

Jeśli chcę pełnego odświeżenia, po prostu zmieniam nazwę folderu na 2014_v2 na moje źródło i zmieniam wewnątrz php na 2014_v2

cały HTML automatycznie się zmienia i pyta o nową ścieżkę, pamięć podręczną MISS w chmurze i żąda jej do źródła.

Przykład: SOURCE.mydomain.com to moje źródło, cloudfront.mydomain.com to CNAME do dystrybucji cloudfront.

Więc PHP nazwał ten plik cloudfront.mydomain.com/2014_v1/javascript.js i kiedy chcę pełnego odświeżenia, po prostu zmieniam nazwę folderu na źródło na „2014_v2” i zmieniam dołączenie PHP, ustawiając folder na „2014_v2” .

W ten sposób nie ma opóźnienia w unieważnieniu i BEZ KOSZTÓW!

To mój pierwszy post w stackoverflow, mam nadzieję, że zrobiłem to dobrze!

MarcoP
źródło
2

W rubinie, używając klejnotu mgły

AWS_ACCESS_KEY = ENV['AWS_ACCESS_KEY_ID']
AWS_SECRET_KEY = ENV['AWS_SECRET_ACCESS_KEY']
AWS_DISTRIBUTION_ID = ENV['AWS_DISTRIBUTION_ID']

conn = Fog::CDN.new(
    :provider => 'AWS',
    :aws_access_key_id => AWS_ACCESS_KEY,
    :aws_secret_access_key => AWS_SECRET_KEY
)

images = ['/path/to/image1.jpg', '/path/to/another/image2.jpg']

conn.post_invalidation AWS_DISTRIBUTION_ID, images

nawet w przypadku unieważnienia przetwarzanie i odświeżanie unieważnienia na wszystkich serwerach Amazon Edge trwa 5–10 minut

Raycchan
źródło
Właśnie uratowałeś mi życie!
Fábio Batista
2

aktualne unieważnienie obsługi AWS CLI w trybie podglądu. Uruchom raz w konsoli następujące czynności:

aws configure set preview.cloudfront true

Wdrażam projekt sieci Web przy użyciu npm. Mam następujące skrypty w moim package.json:

{
    "build.prod": "ng build --prod --aot",
    "aws.deploy": "aws s3 sync dist/ s3://www.mywebsite.com --delete --region us-east-1",
    "aws.invalidate": "aws cloudfront create-invalidation --distribution-id [MY_DISTRIBUTION_ID] --paths /",
    "deploy": "npm run build.prod && npm run aws.deploy && npm run aws.invalidate"
}

Mając powyższe skrypty na miejscu, możesz wdrożyć swoją witrynę za pomocą:

npm run deploy
Dmitry Efimenko
źródło
1
Myślę, że potrzebujesz gwiazdki w poleceniu „aws.invalidate”, zmień --paths /na --paths /*. mój też był taki jak twój i nie unieważnił dystrybucji ...
Herald Smit
1

Jeśli używasz AWS, prawdopodobnie używasz również jego oficjalnego narzędzia CLI (wcześniej czy później). AWS CLI w wersji 1.9.12 lub nowszej obsługuje unieważnianie listy nazw plików.

Pełne ujawnienie: zrobiłem to. Baw się dobrze!

RayLuo
źródło
Martwy link - prowadzi do 404 :( i nie mogę go zaktualizować, ponieważ wersji 1.9.12 brakuje w informacjach o wydaniu ( aws.amazon.com/releasenotes/?tag=releasenotes%23keywords%23cli )
SlyDave
Stary, to była wersja wydana prawie 3 lata temu. Wypróbuj najnowszą wersję, a funkcja prawdopodobnie nadal będzie dostępna. (Pełne ujawnienie: nie pracuję już na AWS CLI.)
RayLuo
och, wiem, po prostu wydało mi się to dziwne, że ze wszystkich notatek wydania, tylko 1.9.12 nie istnieje: D (do tego doszedłem, nie mogąc zaktualizować linku). Ten komentarz był raczej wskazówką dla każdego, kto znalazł się w tym miejscu, tak jak ja i potrzebował znaleźć uwagi do wydania dla interfejsu wiersza polecenia AWS. bez szkody, bez faulu.
SlyDave
0

Idź do CloudFront.

Kliknij swój identyfikator / dystrybucje.

Kliknij Unieważnienia.

Kliknij Utwórz unieważnienie.

W ogromnym przykładowym polu wpisz * i kliknij unieważnij

Gotowe

wprowadź opis obrazu tutaj

Sójka
źródło