Naučio sam ovih 6 lekcija o radu s formacijom oblaka do kraja života.

Počeo sam raditi sa stvaranje oblaka prije 4 godine. Od tada sam pokvario puno infrastruktura, čak i onih koje su već bile u proizvodnji. Ali svaki put kad sam nešto zabrljao, naučio sam nešto novo. Kroz ovo iskustvo podijelit ću neke od najvažnijih lekcija koje sam naučio.

Naučio sam ovih 6 lekcija o radu s formacijom oblaka do kraja života.

Lekcija 1: Testirajte promjene prije nego što ih implementirate

Ovu sam lekciju naučio ubrzo nakon što sam počeo raditi s stvaranje oblaka. Ne sjećam se što sam točno tada pokvario, ali definitivno se sjećam da sam upotrijebio naredbu ažuriranje aws cloudformation. Ova naredba jednostavno izbacuje predložak bez ikakve provjere valjanosti promjena koje će se implementirati. Mislim da nije potrebno nikakvo objašnjenje zašto biste trebali testirati sve promjene prije nego što ih implementirate.

Nakon ovog neuspjeha, odmah sam se promijenio cjevovod za implementaciju, zamjenjujući naredbu za ažuriranje s naredbom stvoriti-promijeniti-postaviti

# OPERATION is either "UPDATE" or "CREATE"
changeset_id=$(aws cloudformation create-change-set 
    --change-set-name "$CHANGE_SET_NAME" 
    --stack-name "$STACK_NAME" 
    --template-body "$TPL_PATH" 
    --change-set-type "$OPERATION" 
    --parameters "$PARAMETERS" 
    --output text 
    --query Id)

aws cloudformation wait 
    change-set-create-complete --change-set-name "$changeset_id"

Nakon što se kreira skup promjena, nema učinka na postojeći stog. Za razliku od naredbe ažuriranja, pristup skupu promjena ne pokreće stvarnu implementaciju. Umjesto toga, stvara popis promjena koje možete pregledati prije implementacije. Promjene možete vidjeti u sučelju aws konzole. Ali ako radije automatizirate sve što možete, provjerite ih u CLI-ju:

# this command is presented only for demonstrational purposes.
# the real command should take pagination into account
aws cloudformation describe-change-set 
    --change-set-name "$changeset_id" 
    --query 'Changes[*].ResourceChange.{Action:Action,Resource:ResourceType,ResourceId:LogicalResourceId,ReplacementNeeded:Replacement}' 
    --output table

Ova bi naredba trebala dati izlaz sličan sljedećem:

--------------------------------------------------------------------
|                         DescribeChangeSet                        |
+---------+--------------------+----------------------+------------+
| Action  | ReplacementNeeded  |      Resource        | ResourceId |
+---------+--------------------+----------------------+------------+
|  Modify | True               |  AWS::ECS::Cluster   |  MyCluster |
|  Replace| True               |  AWS::RDS::DBInstance|  MyDB      |
|  Add    | None               |  AWS::SNS::Topic     |  MyTopic   |
+---------+--------------------+----------------------+------------+

Obratite posebnu pozornost na promjene gdje je Akcija zamijeniti, Izbrisati ili gdje Potrebna zamjena - Istina. To su najopasnije promjene i obično dovode do gubitka informacija.

Nakon što su promjene pregledane, mogu se implementirati

aws cloudformation execute-change-set --change-set-name "$changeset_id"

operation_lowercase=$(echo "$OPERATION" | tr '[:upper:]' '[:lower:]')
aws cloudformation wait "stack-${operation_lowercase}-complete" 
    --stack-name "$STACK_NAME"

Lekcija 2: Koristite pravila snopa da biste spriječili zamjenu ili uklanjanje resursa sa stanjem

Ponekad jednostavno pregledavanje promjena nije dovoljno. Svi smo mi ljudi i svi griješimo. Nedugo nakon što smo počeli koristiti skupove promjena, moj suigrač je nesvjesno izvršio implementaciju koja je rezultirala ažuriranjem baze podataka. Ništa se loše nije dogodilo jer je to bilo okruženje za testiranje.

Iako su naše skripte prikazale popis promjena i tražile potvrdu, promjena Zamijeni je preskočena jer je popis promjena bio toliko velik da nije stao na ekran. A budući da je ovo bilo normalno ažuriranje u testnom okruženju, promjenama se nije obraćala velika pozornost.

Postoje resursi koje nikada ne želite zamijeniti ili ukloniti. To su usluge s punim stanjem, kao što je instanca RDS baze podataka ili elasticsearch klaster, itd. Bilo bi lijepo kada bi aws automatski odbio implementaciju ako bi operacija koja se izvodi zahtijevala brisanje takvog resursa. Srećom, cloudformation ima ugrađeni način za to. To se zove politika snopa, a više o tome možete pročitati u dokumentacija:

STACK_NAME=$1
RESOURCE_ID=$2

POLICY_JSON=$(cat <<EOF
{
    "Statement" : [{
        "Effect" : "Deny",
        "Action" : [
            "Update:Replace",
            "Update:Delete"
        ],
        "Principal": "*",
        "Resource" : "LogicalResourceId/$RESOURCE_ID"
    }]
}
EOF
)

aws cloudformation set-stack-policy --stack-name "$STACK_NAME" 
    --stack-policy-body "$POLICY_JSON"

Lekcija 3: Koristite UsePreviousValue kada ažurirate stog s tajnim parametrima

Kada kreirate RDS mysql entitet, AWS zahtijeva da navedete MasterUsername i MasterUserPassword. Budući da je bolje ne držati tajne u izvornom kodu i htio sam automatizirati apsolutno sve, implementirao sam "pametni mehanizam" gdje će se vjerodajnice prije implementacije dobiti od s3, a ako se vjerodajnice ne pronađu, generiraju se nove vjerodajnice i pohranjeno u s3.

Te će vjerodajnice zatim biti proslijeđene kao parametri naredbi za kreiranje-promjenu-postavljanje forme oblaka. Dok sam eksperimentirao sa skriptom, dogodilo se da je veza sa s3 izgubljena, a moj “pametni mehanizam” je to tretirao kao signal za generiranje novih vjerodajnica.

Ako počnem koristiti ovu skriptu u produkciji i ponovno se pojavi problem s vezom, ažurirat će stog s novim vjerodajnicama. U ovom konkretnom slučaju neće se dogoditi ništa loše. Međutim, napustio sam ovaj pristup i počeo koristiti drugi, dajući vjerodajnice samo jednom - prilikom stvaranja stoga. I kasnije, kada stog treba ažurirati, umjesto navođenja tajne vrijednosti parametra, jednostavno bih upotrijebio UsePreviousValue=true:

aws cloudformation create-change-set 
    --change-set-name "$CHANGE_SET_NAME" 
    --stack-name "$STACK_NAME" 
    --template-body "$TPL_PATH" 
    --change-set-type "UPDATE" 
    --parameters "ParameterKey=MasterUserPassword,UsePreviousValue=true"

Lekcija 4: Koristite konfiguraciju vraćanja

Drugi tim s kojim sam radio koristio je tu funkciju stvaranje oblakanazvao povratna konfiguracija. Nisam prije toga naišao i brzo sam shvatio da će to učiniti raspoređivanje mojih gomila još cool. Sada ga koristim svaki put kada implementiram svoj kod na lambda ili ECS koristeći cloudformation.

Kako to radi: vi odredite CloudWatch alarm u parametru --povratak-konfiguracijakada kreirate skup promjena. Kasnije, kada izvršite niz promjena, aws nadzire alarm najmanje jednu minutu. Vraća implementaciju ako alarm tijekom tog vremena promijeni stanje u ALARM.

Ispod je primjer izvatka predloška stvaranje oblakau kojoj stvaram cloudwatch alarm, koji prati korisničku metriku oblaka kao broj pogrešaka u zapisima oblaka (metrika se generira putem Metrički filtar):

Resources:
  # this metric tracks number of errors in the cloudwatch logs. In this
  # particular case it's assumed logs are in json format and the error logs are
  # identified by level "error". See FilterPattern
  ErrorMetricFilter:
    Type: AWS::Logs::MetricFilter
    Properties:
      LogGroupName: !Ref LogGroup
      FilterPattern: !Sub '{$.level = "error"}'
      MetricTransformations:
      - MetricNamespace: !Sub "${AWS::StackName}-log-errors"
        MetricName: Errors
        MetricValue: 1
        DefaultValue: 0

  ErrorAlarm:
    Type: AWS::CloudWatch::Alarm
    Properties:
      AlarmName: !Sub "${AWS::StackName}-errors"
      Namespace: !Sub "${AWS::StackName}-log-errors"
      MetricName: Errors
      Statistic: Maximum
      ComparisonOperator: GreaterThanThreshold
      Period: 1 # 1 minute
      EvaluationPeriods: 1
      Threshold: 0
      TreatMissingData: notBreaching
      ActionsEnabled: yes

Sada alarm može se koristiti kao povrat na staro okidač prilikom izvođenja okvira s alatima:

ALARM_ARN=$1

ROLLBACK_TRIGGER=$(cat <<EOF
{
  "RollbackTriggers": [
    {
      "Arn": "$ALARM_ARN",
      "Type": "AWS::CloudWatch::Alarm"
    }
  ],
  "MonitoringTimeInMinutes": 1
}
EOF
)

aws cloudformation create-change-set 
    --change-set-name "$CHANGE_SET_NAME" 
    --stack-name "$STACK_NAME" 
    --template-body "$TPL_PATH" 
    --change-set-type "UPDATE" 
    --rollback-configuration "$ROLLBACK_TRIGGER"

Lekcija 5: Provjerite jeste li implementirali najnoviju verziju predloška

Lako je implementirati verziju koja nije najnovija od predloška cloudformation, ali to će uzrokovati mnogo štete. Ovo nam se jednom dogodilo: programer nije gurnuo najnovije promjene iz Gita i nesvjesno je postavio prethodnu verziju stoga. To je dovelo do prekida rada aplikacije koja je koristila ovaj hrp.

Nešto tako jednostavno poput dodavanja provjere da li je grana ažurna prije nego što se posvetite njoj, bilo bi u redu (pod pretpostavkom da je git vaš alat za kontrolu verzija):

git fetch
HEADHASH=$(git rev-parse HEAD)
UPSTREAMHASH=$(git rev-parse master@{upstream})

if [[ "$HEADHASH" != "$UPSTREAMHASH" ]] ; then
   echo "Branch is not up to date with origin. Aborting"
   exit 1
fi

Lekcija 6: Nemojte ponovno izmišljati kotač

Može se činiti kao raspoređivanje sa stvaranje oblaka - to je lako. Trebate samo hrpu bash skripti koje izvršavaju aws cli naredbe.

Prije 4 godine počeo sam s jednostavnim skriptama pod nazivom aws cloudformation create-stack naredba. Ubrzo scenarij više nije bio jednostavan. Svaka naučena lekcija činila je scenarij sve složenijim. Ne samo da je bilo teško, već i puno grešaka.

Trenutno radim u malom IT odjelu. Iskustvo je pokazalo da svaki tim ima vlastiti način postavljanja hrpa oblaka. I to je loše. Bilo bi bolje da svi imaju isti pristup. Srećom, postoji mnogo dostupnih alata koji vam mogu pomoći u postavljanju i konfiguriranju hrpa oblaka.

Ove lekcije pomoći će vam da izbjegnete pogreške.

Izvor: www.habr.com

Dodajte komentar