Bash Scripting Awọn iṣe ti o dara julọ: Itọsọna iyara si Gbẹkẹle ati Awọn iwe afọwọkọ Bash Ṣiṣẹ

Bash Scripting Awọn iṣe ti o dara julọ: Itọsọna iyara si Gbẹkẹle ati Awọn iwe afọwọkọ Bash Ṣiṣẹ
Ikarahun ogiri nipasẹ manapi

N ṣatunṣe aṣiṣe awọn iwe afọwọkọ bash dabi wiwa fun abẹrẹ kan ninu haystack, ni pataki nigbati awọn afikun tuntun ba han ni koodu koodu ti o wa laisi ero akoko ti awọn ọran ti eto, gedu ati igbẹkẹle. O le rii ararẹ ni iru awọn ipo boya nitori awọn aṣiṣe tirẹ tabi nigbati o n ṣakoso awọn akopọ ti awọn iwe afọwọkọ.

Egbe Mail.ru awọsanma Solutions tumọ nkan kan pẹlu awọn iṣeduro ti yoo ṣe iranlọwọ fun ọ lati kọ, ṣatunṣe ati ṣetọju awọn iwe afọwọkọ rẹ dara julọ. Gbagbọ tabi rara, ko si ohun ti o lu itelorun ti kikọ mimọ, koodu bash ti o ṣetan lati lo ti o ṣiṣẹ ni gbogbo igba.

Ninu àpilẹkọ naa, onkọwe pin ohun ti o ti kọ ni awọn ọdun diẹ sẹhin, ati diẹ ninu awọn aṣiṣe ti o wọpọ ti o ti mu u kuro ni iṣọ. Eyi ṣe pataki nitori pe gbogbo idagbasoke sọfitiwia, ni aaye diẹ ninu iṣẹ wọn, ṣiṣẹ pẹlu awọn iwe afọwọkọ lati ṣe adaṣe awọn iṣẹ ṣiṣe ṣiṣe deede.

Awọn olutọju pakute

Pupọ awọn iwe afọwọkọ bash ti Mo ti pade rara ko lo ẹrọ isọdi ti o munadoko nigbati nkan airotẹlẹ ba ṣẹlẹ lakoko ipaniyan iwe afọwọkọ.

Awọn iyanilẹnu le dide lati ita, gẹgẹbi gbigba ifihan agbara lati inu mojuto. Mimu iru awọn ọran jẹ pataki pupọ lati rii daju pe awọn iwe afọwọkọ jẹ igbẹkẹle to lati ṣiṣẹ lori awọn eto iṣelọpọ. Nigbagbogbo Mo lo awọn olutọju ijade lati dahun si awọn oju iṣẹlẹ bii eyi:

function handle_exit() {
  // Add cleanup code here
  // for eg. rm -f "/tmp/${lock_file}.lock"
  // exit with an appropriate status code
}
  
// trap <HANDLER_FXN> <LIST OF SIGNALS TO TRAP>
trap handle_exit 0 SIGHUP SIGINT SIGQUIT SIGABRT SIGTERM

trap jẹ aṣẹ ti a ṣe sinu ikarahun ti o ṣe iranlọwọ fun ọ lati forukọsilẹ iṣẹ afọmọ ti a pe ni ọran eyikeyi awọn ifihan agbara. Sibẹsibẹ, itọju pataki yẹ ki o ṣe pẹlu awọn olutọju bii SIGINT, eyi ti o fa ki iwe afọwọkọ ṣẹyun.

Ni afikun, ni ọpọlọpọ igba o yẹ ki o mu nikan EXIT, ṣugbọn awọn agutan ni wipe o le kosi ṣe awọn ihuwasi ti awọn akosile fun kọọkan kọọkan ifihan agbara.

Awọn iṣẹ iṣeto ti a ṣe sinu - ifopinsi iyara lori aṣiṣe

O ṣe pataki pupọ lati dahun si awọn aṣiṣe ni kete ti wọn ba waye ati da ipaniyan duro ni kiakia. Ko si ohun ti o le buru ju tẹsiwaju lati ṣiṣe aṣẹ bi eleyi:

rm -rf ${directory_name}/*

Jọwọ ṣe akiyesi pe oniyipada naa directory_name ko pinnu.

O ṣe pataki lati lo awọn iṣẹ ti a ṣe sinu lati mu iru awọn oju iṣẹlẹ set, bi eleyi set -o errexit, set -o pipefail tabi set -o nounset ni ibere ti awọn akosile. Awọn iṣẹ wọnyi rii daju pe iwe afọwọkọ rẹ yoo jade ni kete ti o ba pade eyikeyi koodu ijade ti kii-odo, lilo awọn oniyipada ti ko ṣe alaye, awọn aṣẹ aiṣedeede ti o kọja lori paipu, ati bẹbẹ lọ:

#!/usr/bin/env bash

set -o errexit
set -o nounset
set -o pipefail

function print_var() {
  echo "${var_value}"
}

print_var

$ ./sample.sh
./sample.sh: line 8: var_value: unbound variable

akiyesi: -itumọ ti ni awọn iṣẹ bi set -o errexit, yoo jade kuro ni akosile ni kete ti koodu ipadabọ "aise" wa (miiran ju odo). Nitorinaa o dara lati ṣafihan mimu aṣiṣe aṣa, fun apẹẹrẹ:

#!/bin/bash
error_exit() {
  line=$1
  shift 1
  echo "ERROR: non zero return code from line: $line -- $@"
  exit 1
}
a=0
let a++ || error_exit "$LINENO" "let operation returned non 0 code"
echo "you will never see me"
# run it, now we have useful debugging output
$ bash foo.sh
ERROR: non zero return code from line: 9 -- let operation returned non 0 code

Kikọ awọn iwe afọwọkọ ni ọna yii fi agbara mu ọ lati ṣọra diẹ sii nipa ihuwasi ti gbogbo awọn aṣẹ ti o wa ninu iwe afọwọkọ ati nireti iṣeeṣe aṣiṣe ṣaaju ki o to mu ọ ni iyalẹnu.

ShellCheck lati ṣawari awọn aṣiṣe lakoko idagbasoke

O tọ lati ṣepọ nkan bii ShellCheck sinu idagbasoke rẹ ati idanwo awọn opo gigun ti epo lati ṣayẹwo koodu bash rẹ lodi si awọn iṣe ti o dara julọ.

Mo lo ni awọn agbegbe idagbasoke agbegbe mi lati gba awọn ijabọ lori sintasi, awọn atunmọ, ati diẹ ninu awọn aṣiṣe ninu koodu ti MO le ti padanu lakoko idagbasoke. Eyi jẹ ohun elo itupalẹ aimi fun awọn iwe afọwọkọ bash rẹ ati pe Mo ṣeduro gaan ni lilo rẹ.

Lilo awọn koodu ijade tirẹ

Awọn koodu ipadabọ ni POSIX kii ṣe odo tabi ẹyọkan, ṣugbọn odo tabi iye ti kii ṣe odo. Lo awọn ẹya wọnyi lati da awọn koodu aṣiṣe aṣa pada (laarin 201-254) fun ọpọlọpọ awọn aṣiṣe aṣiṣe.

Alaye yii le ṣee lo nipasẹ awọn iwe afọwọkọ miiran ti o fi ipari si tirẹ lati ni oye gangan iru aṣiṣe ti o ṣẹlẹ ati fesi ni ibamu:

#!/usr/bin/env bash

SUCCESS=0
FILE_NOT_FOUND=240
DOWNLOAD_FAILED=241

function read_file() {
  if ${file_not_found}; then
    return ${FILE_NOT_FOUND}
  fi
}

akiyesi: jọwọ ṣọra paapaa pẹlu awọn orukọ oniyipada ti o ṣalaye lati yago fun awọn oniyipada agbegbe ti o bori lairotẹlẹ.

Awọn iṣẹ titẹ sii

Lẹwa ati eto gedu jẹ pataki lati ni irọrun loye awọn abajade ti iwe afọwọkọ rẹ. Gẹgẹbi pẹlu awọn ede siseto ipele giga, Mo nigbagbogbo lo awọn iṣẹ gedu abinibi ni awọn iwe afọwọkọ bash mi, gẹgẹbi __msg_info, __msg_error ati bẹ lori.

Eyi ṣe iranlọwọ lati pese eto gedu iwọnwọn nipasẹ ṣiṣe awọn ayipada ni aaye kan nikan:

#!/usr/bin/env bash

function __msg_error() {
    [[ "${ERROR}" == "1" ]] && echo -e "[ERROR]: $*"
}

function __msg_debug() {
    [[ "${DEBUG}" == "1" ]] && echo -e "[DEBUG]: $*"
}

function __msg_info() {
    [[ "${INFO}" == "1" ]] && echo -e "[INFO]: $*"
}

__msg_error "File could not be found. Cannot proceed"

__msg_debug "Starting script execution with 276MB of available RAM"

Mo maa n gbiyanju lati ni iru ẹrọ kan ninu awọn iwe afọwọkọ mi __init, nibiti iru awọn oniyipada logger ati awọn oniyipada eto miiran ti wa ni ipilẹṣẹ tabi ṣeto si awọn iye aiyipada. Awọn oniyipada wọnyi le tun ṣeto lati awọn aṣayan laini aṣẹ lakoko ẹbẹ iwe afọwọkọ.

Fun apẹẹrẹ, nkankan bi:

$ ./run-script.sh --debug

Nigbati iru iwe afọwọkọ kan ba ti ṣiṣẹ, o rii daju pe awọn eto jakejado eto ti ṣeto si awọn iye aiyipada ti wọn ba nilo, tabi o kere ju ti ipilẹṣẹ si nkan ti o yẹ ti o ba jẹ dandan.

Mo nigbagbogbo ṣe ipilẹ yiyan kini lati ṣe ipilẹṣẹ ati kini kii ṣe lori iṣowo-pipa laarin wiwo olumulo ati awọn alaye ti awọn atunto ti olumulo le / yẹ ki o lọ sinu.

Faaji fun ilotunlo ati ipo eto mimọ

Modular / reusable koodu

├── framework
│   ├── common
│   │   ├── loggers.sh
│   │   ├── mail_reports.sh
│   │   └── slack_reports.sh
│   └── daily_database_operation.sh

Mo tọju ibi ipamọ lọtọ ti MO le lo lati ṣe ipilẹṣẹ iṣẹ akanṣe tuntun / iwe afọwọkọ bash ti Mo fẹ lati dagbasoke. Ohunkohun ti o le tun lo ni a le fipamọ sinu ibi ipamọ kan ati gba pada nipasẹ awọn iṣẹ akanṣe miiran ti o fẹ lati lo iṣẹ ṣiṣe yẹn. Ṣiṣeto awọn iṣẹ akanṣe ni ọna yii dinku iwọn awọn iwe afọwọkọ miiran ati tun ṣe idaniloju pe ipilẹ koodu jẹ kekere ati rọrun lati ṣe idanwo.

Bi ninu apẹẹrẹ loke, gbogbo awọn iṣẹ gedu bii __msg_info, __msg_error ati awọn miiran, gẹgẹbi awọn ijabọ Slack, wa ninu lọtọ ni common/* ati ki o dynamically sopọ ni miiran awọn oju iṣẹlẹ bi daily_database_operation.sh.

Fi sile kan mọ eto

Ti o ba n ṣajọpọ awọn ohun elo eyikeyi lakoko ti iwe afọwọkọ n ṣiṣẹ, o gba ọ niyanju lati tọju gbogbo iru data bẹ sinu itọsọna ti o pin pẹlu orukọ laileto, fun apẹẹrẹ. /tmp/AlRhYbD97/*. O le lo awọn olupilẹṣẹ ọrọ laileto lati yan orukọ itọsọna naa:

rand_dir_name="$(cat /dev/urandom | tr -dc 'a-zA-Z0-9' | fold -w 16 | head -n 1)"

Lẹhin ti pari iṣẹ, nu ti iru awọn ilana le wa ni pese ni awọn kio handlers sísọ loke. Ti a ko ba ṣe abojuto awọn ilana igba diẹ, wọn kojọpọ ati ni awọn ipele kan fa awọn iṣoro airotẹlẹ lori agbalejo, gẹgẹbi disk kikun.

Lilo awọn faili titiipa

Nigbagbogbo o nilo lati rii daju pe apẹẹrẹ kan nikan ti iwe afọwọkọ kan nṣiṣẹ lori agbalejo ni akoko eyikeyi. Eyi le ṣee ṣe nipa lilo awọn faili titiipa.

Mo maa ṣẹda awọn faili titiipa sinu /tmp/project_name/*.lock ati ṣayẹwo fun wiwa wọn ni ibẹrẹ ti iwe afọwọkọ naa. Eyi ṣe iranlọwọ fun iwe afọwọkọ lati fopin si oore-ọfẹ ati yago fun awọn ayipada airotẹlẹ si ipo eto nipasẹ iwe afọwọkọ miiran ti nṣiṣẹ ni afiwe. Awọn faili titiipa ko nilo ti o ba nilo iwe afọwọkọ kanna lati ṣiṣẹ ni afiwe lori agbalejo ti a fun.

Ṣe iwọn ati ilọsiwaju

Nigbagbogbo a nilo lati ṣiṣẹ pẹlu awọn iwe afọwọkọ ti o ṣiṣẹ lori awọn akoko pipẹ, gẹgẹbi awọn iṣẹ data ojoojumọ. Iru awọn iṣẹ ṣiṣe ni igbagbogbo kan awọn ọna ti o tẹle: data ikojọpọ, ṣiṣayẹwo fun awọn aiṣedeede, gbigbe data wọle, fifiranṣẹ awọn ijabọ ipo, ati bẹbẹ lọ.

Ni iru awọn ọran naa, Mo nigbagbogbo gbiyanju lati fọ iwe afọwọkọ naa si awọn iwe afọwọkọ kekere lọtọ ati jabo ipo wọn ati akoko ipaniyan nipa lilo:

time source "${filepath}" "${args}">> "${LOG_DIR}/RUN_LOG" 2>&1

Nigbamii Mo le wo akoko ipaniyan pẹlu:

tac "${LOG_DIR}/RUN_LOG.txt" | grep -m1 "real"

Eyi ṣe iranlọwọ fun mi lati ṣe idanimọ iṣoro / awọn agbegbe ti o lọra ni awọn iwe afọwọkọ ti o nilo iṣapeye.

Ti o dara orire!

Kini ohun miiran lati ka:

  1. Lọ ki o si GPU caches.
  2. Apeere ti ohun elo-iṣẹlẹ ti o da lori awọn oju opo wẹẹbu ni ibi ipamọ ohun elo S3 ti Mail.ru Cloud Solutions.
  3. ikanni Telegram wa nipa iyipada oni-nọmba.

orisun: www.habr.com

Fi ọrọìwòye kun