IlmHamroh
Python kursi/Paketlash va chiqarish6/8-dars17 daqiqa
Mundarija (22)

19.6-dars: CLI dastur yaratish

19-QISM — PAKETLASH VA CHIQARISH · 6-dars


1. Kirish va motivatsiya

Ko'p Python vosita terminaldan ishlatiladi: pip, pytest, ruff, black — hammasi CLI (Command-Line Interface — buyruq qatori interfeysi) dastur. Foydalanuvchi pytest -v tests/ yozadi va dastur argumentlarni (-v, tests/) o'qib, mos ish qiladi. O'z kutubxonangizni CLI vosita sifatida taqdim qilsangiz, uni har kim terminaldan qulay ishlatadi. CLI — dasturingizni foydalanuvchiga yetkazishning eng keng tarqalgan usullaridan biri.

Python CLI qurish uchun ikki asosiy vosita beradi: argparse (standart kutubxona) va click (qulayroq, tashqi). Ular argumentlarni tahlil qiladi, yordam yaratadi va xatolarni boshqaradi.

Real vaziyat. Bir dasturchi foydali skriptini hamkasblariga tarqatdi — u argumentlarni sys.argv[1], sys.argv[2] bilan qo'lda o'qirdi. Muammolar: argument tartibi noto'g'ri bo'lsa chalkash xato, yordam yo'q (--help ishlamasdi), noto'g'ri tur (int kutilganda satr) tushunarsiz yiqildi. Hamkasblar skriptni ishlatolmasdi. U argparse ga o'tdi: endi --help avtomatik yordam berdi, noto'g'ri argument aniq xato ko'rsatdi, turlar tekshirildi. Keyin [project.scripts] 19.2-bob bilan uni haqiqiy buyruqga aylantirdi — wisar deb terminalda yozib ishlatila boshladi. Professional CLI skriptni "vosita" ga aylantirdi.

Bu darsda CLI dastur yaratishni o'rganamiz.

Bu darsda:

  • CLI nima va tuzilishi
  • argparse — pozitsion, ixtiyoriy, bayroqlar
  • Yordam va xatolar (avtomatik)
  • Ost-buyruqlar (subcommands)
  • click — qulayroq alternativa
  • CLI ni test qilish
  • [project.scripts] bilan buyruq yaratish
  • Amaliy: to'liq CLI vosita

ℹ argparse — standart kutubxonada; click — tashqi. Misollarda prog= bilan deterministik yordam matni ko'rsatiladi.


2. Nazariya — chuqur tushuntirish

2.1. CLI tuzilishi

Buyruq qatori argumentlari:

wisar salom Aziz --necha 3 --katta
  │     │    │      │         │
buyruq ost- pozit-  ixtiyoriy bayroq
      buyruq sion   (qiymatli) (qiymatsiz)
Tur Misol Ma'nosi
Pozitsion Aziz Tartibga bog'liq, majburiy
Ixtiyoriy --necha 3 Nomli, qiymatli
Bayroq --katta Nomli, qiymatsiz (bor/yo'q)
Ost-buyruq salom Rejim tanlash

2.2. argparse asoslari

python
import argparse

parser = argparse.ArgumentParser(prog="wisar", description="Wisar CLI")
parser.add_argument("ism", help="foydalanuvchi ismi")          # pozitsion
parser.add_argument("-n", "--necha", type=int, default=1)      # ixtiyoriy
parser.add_argument("--katta", action="store_true")            # bayroq
args = parser.parse_args()

print(args.ism, args.necha, args.katta)
Element Nima
ArgumentParser Parser yaratadi
add_argument Argument qo'shadi
type=int Turni tekshiradi/aylantiradi
default Sukut qiymat
action="store_true" Bayroq (bor→True)
parse_args() sys.argv ni tahlil qiladi

2.3. Yordam va xatolar

argparse avtomatik:

Imkoniyat Tafsilot
--help/-h Yordam matni (add_argument dan)
Xato xabari Noto'g'ri argument aniq ko'rsatiladi
Tur tekshiruvi type=int ga satr → xato
usage qatori Qanday ishlatishni ko'rsatadi
usage: wisar [-h] [-n NECHA] [--katta] ism

argparse yordam va xato boshqaruvini bepul beradi — sys.argv ni qo'lda o'qishdan asosiy afzallik.

2.4. Ost-buyruqlar (subcommands)

Murakkab CLI (masalan git commit, git push) ost-buyruqlarga bo'linadi:

python
parser = argparse.ArgumentParser(prog="wisar")
sub = parser.add_subparsers(dest="buyruq")

salom_p = sub.add_parser("salom", help="salomlashadi")
salom_p.add_argument("kimga")

export_p = sub.add_parser("export", help="eksport qiladi")
export_p.add_argument("--format", choices=["csv", "json"])
bash
wisar salom Aziz
wisar export --format csv

Ost-buyruqlar — har biri o'z argumentlariga ega alohida rejim (git add, git commit kabi).

2.5. click — qulayroq alternativa

click — dekoratorlar bilan CLI qurish (argparse'dan ergonomikroq):

python
import click

@click.command()
@click.argument("ism")
@click.option("-n", "--necha", default=1, help="necha marta")
@click.option("--katta", is_flag=True, help="katta harflar")
def salom(ism, necha, katta):
    """Foydalanuvchini salomlaydi."""
    matn = f"Salom, {ism}!"
    if katta:
        matn = matn.upper()
    for _ in range(necha):
        click.echo(matn)
click afzalligi Tafsilot
Dekoratorlar Funksiya + dekorator = buyruq
Docstring → yordam Avtomatik
Turlar, tekshiruv Boy
Rangli chiqish click.echo, click.style
Ost-buyruqlar @click.group()

2.6. CLI ni test qilish

CLI ham test qilinadi (17-qism):

python
from click.testing import CliRunner

def test_salom():
    natija = CliRunner().invoke(salom, ["Aziz", "--katta"])
    assert natija.exit_code == 0
    assert "SALOM, AZIZ!" in natija.output

click.testing.CliRunner — CLI ni ishga tushirmasdan, dasturiy sinash. argparse uchun parse_args([...]) ga ro'yxat berib sinaladi.

2.7. [project.scripts] bilan buyruq

CLI ni haqiqiy terminal buyrug'iga aylantirish 19.2-bob:

toml
[project.scripts]
wisar = "wisar.cli:main"        # 'wisar' buyrug'i → wisar/cli.py dagi main()

O'rnatilgach:

bash
pip install wisar
wisar salom Aziz               # to'g'ridan-to'g'ri buyruq

[project.scripts] — CLI funksiyani terminal buyrug'iga bog'laydi: python -m yoki uzun yo'l shart emas.

2.8. Yaxshi CLI dizayni

Tamoyil Tafsilot
Yordam --help har buyruqda aniq
Chiqish kodi 0 — muvaffaqiyat, 0 emas — xato
Xato — stderr ga Chiqish (natija) — stdout, xato — stderr
Aniq xabar Noto'g'ri kirishda aniq xato
Standart konvensiya -h, --version, -v
Oqim Katta chiqishda oqim (16.8)

Yaxshi CLI — foydalanuvchiga tushunarli: aniq yordam, mos chiqish kodlari, xatoni stderr ga.


3. Tez ma'lumotnoma

python
# argparse
import argparse
p = argparse.ArgumentParser(prog="wisar", description="...")
p.add_argument("ism")                          # pozitsion
p.add_argument("-n", "--necha", type=int, default=1)   # ixtiyoriy
p.add_argument("--katta", action="store_true")  # bayroq
args = p.parse_args()

# click
import click
@click.command()
@click.argument("ism")
@click.option("--necha", default=1)
def cli(ism, necha): click.echo(...)
toml
[project.scripts]
wisar = "wisar.cli:main"

Qoidalar

argparse (stdlib) yoki click (qulay)
pozitsion (majburiy), ixtiyoriy (--), bayroq (store_true/is_flag)
--help va xatolar avtomatik
ost-buyruqlar — add_subparsers / @click.group
CLI ni test qiling (CliRunner / parse_args)
[project.scripts] — terminal buyrug'i
xato → stderr, chiqish kodi → 0/1

4. Batafsil misollar

Misollarda argparse prog= bilan (deterministik) va click CliRunner bilan ishlatiladi.

Misol 1 — argparse asoslari

python
"""argparse: pozitsion, ixtiyoriy, bayroq; type tekshiruvi; default; avtomatik yordam va usage; parse_args ro'yxat bilan sinash."""

import argparse
import contextlib
import io


def parser_yasa() -> argparse.ArgumentParser:
    p = argparse.ArgumentParser(prog="wisar", description="Wisar salomlash vositasi")
    p.add_argument("ism", help="foydalanuvchi ismi")
    p.add_argument("-n", "--necha", type=int, default=1, help="necha marta salomlash")
    p.add_argument("--katta", action="store_true", help="katta harflar bilan")
    return p


def main() -> None:
    p = parser_yasa()

    print("=== 1. Argumentlarni tahlil qilish ===")
    args = p.parse_args(["Aziz", "-n", "3", "--katta"])
    print(f"  ism={args.ism}, necha={args.necha}, katta={args.katta}")

    print("\n=== 2. Sukut qiymatlar ===")
    args = p.parse_args(["Bek"])
    print(f"  ism={args.ism}, necha={args.necha} (sukut), katta={args.katta} (sukut)")

    print("\n=== 3. Salomlash mantig'i ===")
    args = p.parse_args(["Malika", "-n", "2", "--katta"])
    matn = f"Salom, {args.ism}!"
    if args.katta:
        matn = matn.upper()
    for _ in range(args.necha):
        print(f"  {matn}")

    print("\n=== 4. Avtomatik yordam ===")
    buf = io.StringIO()
    with contextlib.redirect_stdout(buf):
        with contextlib.suppress(SystemExit):
            p.parse_args(["--help"])
    for qator in buf.getvalue().splitlines():
        print(f"  {qator}")


if __name__ == "__main__":
    main()

Natijaning muhim qismi:

text
=== 1. Argumentlarni tahlil qilish ===
  ism=Aziz, necha=3, katta=True

=== 2. Sukut qiymatlar ===
  ism=Bek, necha=1 (sukut), katta=False (sukut)

=== 3. Salomlash mantig'i ===
  SALOM, MALIKA!
  SALOM, MALIKA!

=== 4. Avtomatik yordam ===
  usage: wisar [-h] [-n NECHA] [--katta] ism

  Wisar salomlash vositasi

  positional arguments:
    ism                foydalanuvchi ismi

  options:
    -h, --help         show this help message and exit
    -n, --necha NECHA  necha marta salomlash
    --katta            katta harflar bilan

Nima ko'rsatdi: 2.1, 2.2, 2.3-bo'limlar.

Misol 2 — Ost-buyruqlar (subcommands)

python
"""argparse ost-buyruqlar: add_subparsers; har buyruq o'z argumentlariga ega; choices bilan cheklash; buyruqqa qarab ish."""

import argparse
import contextlib
import io


def parser_yasa() -> argparse.ArgumentParser:
    p = argparse.ArgumentParser(prog="wisar", description="Wisar vositasi")
    sub = p.add_subparsers(dest="buyruq", required=True)

    salom_p = sub.add_parser("salom", help="foydalanuvchini salomlaydi")
    salom_p.add_argument("ism")

    export_p = sub.add_parser("export", help="ma'lumotni eksport qiladi")
    export_p.add_argument("--format", choices=["csv", "json"], default="json")

    return p


def bajar(args) -> str:
    if args.buyruq == "salom":
        return f"Salom, {args.ism}!"
    if args.buyruq == "export":
        return f"{args.format} formatida eksport qilindi"
    return "noma'lum"


def main() -> None:
    p = parser_yasa()

    print("=== 1. salom ost-buyrug'i ===")
    args = p.parse_args(["salom", "Aziz"])
    print(f"  buyruq={args.buyruq}, natija: {bajar(args)}")

    print("\n=== 2. export ost-buyrug'i ===")
    args = p.parse_args(["export", "--format", "csv"])
    print(f"  buyruq={args.buyruq}, format={args.format}, natija: {bajar(args)}")

    print("\n=== 3. export sukut format ===")
    args = p.parse_args(["export"])
    print(f"  format={args.format} (sukut), natija: {bajar(args)}")

    print("\n=== 4. choices tekshiruvi ===")
    buf = io.StringIO()
    xato_bor = False
    with contextlib.redirect_stderr(buf):
        with contextlib.suppress(SystemExit):
            p.parse_args(["export", "--format", "xml"])
            xato_bor = False
        else_xato = "invalid choice" in buf.getvalue()
    print(f"  'xml' noto'g'ri format (invalid choice): {else_xato}")
    print("  ⭐ choices=['csv','json'] noto'g'ri qiymatni rad etadi")

    print("\n=== 5. Yordam (usage) ===")
    buf = io.StringIO()
    with contextlib.redirect_stdout(buf):
        with contextlib.suppress(SystemExit):
            p.parse_args(["--help"])
    for qator in buf.getvalue().splitlines()[:3]:
        print(f"  {qator}")


if __name__ == "__main__":
    main()

Natijaning muhim qismi:

text
=== 1. salom ost-buyrug'i ===
  buyruq=salom, natija: Salom, Aziz!

=== 2. export ost-buyrug'i ===
  buyruq=export, format=csv, natija: csv formatida eksport qilindi

=== 3. export sukut format ===
  format=json (sukut), natija: json formatida eksport qilindi

=== 4. choices tekshiruvi ===
  'xml' noto'g'ri format (invalid choice): True
  ⭐ choices=['csv','json'] noto'g'ri qiymatni rad etadi

=== 5. Yordam (usage) ===
  usage: wisar [-h] {salom,export} ...

  Wisar vositasi

Nima ko'rsatdi: 2.4-bo'lim.

Misol 3 — click va CLI ni test qilish

python
"""click dekoratorlar bilan CLI; docstring → yordam; is_flag bayroq; CliRunner bilan test; exit_code va output."""

import click
from click.testing import CliRunner


@click.command()
@click.argument("ism")
@click.option("-n", "--necha", default=1, help="necha marta salomlash")
@click.option("--katta", is_flag=True, help="katta harflar bilan")
def salom(ism, necha, katta):
    """Foydalanuvchini salomlaydi."""
    matn = f"Salom, {ism}!"
    if katta:
        matn = matn.upper()
    for _ in range(necha):
        click.echo(matn)


def main() -> None:
    runner = CliRunner()

    print("=== 1. Oddiy chaqiruv ===")
    natija = runner.invoke(salom, ["Aziz"])
    print(f"  exit_code: {natija.exit_code}")
    print(f"  chiqish: {natija.output.strip()}")

    print("\n=== 2. Bayroq va option ===")
    natija = runner.invoke(salom, ["Bek", "-n", "2", "--katta"])
    for qator in natija.output.splitlines():
        print(f"  {qator}")

    print("\n=== 3. CLI ni test qilish (17-qism) ===")
    natija = runner.invoke(salom, ["Malika", "--katta"])
    print(f"  exit_code == 0: {natija.exit_code == 0}")
    print(f"  'SALOM, MALIKA!' chiqishda: {'SALOM, MALIKA!' in natija.output}")

    print("\n=== 4. Avtomatik yordam (docstring dan) ===")
    natija = runner.invoke(salom, ["--help"])
    for qator in natija.output.splitlines():
        print(f"  {qator}")


if __name__ == "__main__":
    main()

Natijaning muhim qismi:

text
=== 1. Oddiy chaqiruv ===
  exit_code: 0
  chiqish: Salom, Aziz!

=== 2. Bayroq va option ===
  SALOM, BEK!
  SALOM, BEK!

=== 3. CLI ni test qilish (17-qism) ===
  exit_code == 0: True
  'SALOM, MALIKA!' chiqishda: True

=== 4. Avtomatik yordam (docstring dan) ===
  Usage: salom [OPTIONS] ISM

    Foydalanuvchini salomlaydi.

  Options:
    -n, --necha INTEGER  necha marta salomlash
    --katta              katta harflar bilan
    --help               Show this message and exit.

Nima ko'rsatdi: 2.5, 2.6-bo'limlar.

Misol 4 — Amaliy: to'liq CLI vosita

Vazifalarni boshqaruvchi to'liq CLI vosita yaratamiz: ost-buyruqlar (qosh, royxat, bajar), argumentlar, bayroqlar va yordam bilan. Uni click.group bilan quramiz, CliRunner bilan test qilamiz va [project.scripts] bilan qanday buyruqga aylanishini ko'rsatamiz. Bu — real CLI vositaning namunasi.

python
"""to'liq CLI: click.group ost-buyruqlar (qosh, royxat, bajar); argumentlar, bayroqlar; CliRunner test; [project.scripts] integratsiyasi."""

import click
from click.testing import CliRunner

# Soddalashtirilgan holat (xotirada)
VAZIFALAR: list[dict] = []


@click.group()
def cli():
    """Wisar vazifa boshqaruvchisi."""


@cli.command()
@click.argument("matn")
@click.option("--muhim", is_flag=True, help="muhim vazifa")
def qosh(matn, muhim):
    """Yangi vazifa qo'shadi."""
    VAZIFALAR.append({"matn": matn, "muhim": muhim, "bajarildi": False})
    click.echo(f"Qo'shildi: {matn}" + (" (muhim)" if muhim else ""))


@cli.command()
@click.option("--faqat-muhim", is_flag=True, help="faqat muhimlar")
def royxat(faqat_muhim):
    """Vazifalar ro'yxatini ko'rsatadi."""
    for i, v in enumerate(VAZIFALAR, 1):
        if faqat_muhim and not v["muhim"]:
            continue
        belgi = "✓" if v["bajarildi"] else " "
        muhim = "!" if v["muhim"] else " "
        click.echo(f"[{belgi}]{muhim} {i}. {v['matn']}")


@cli.command()
@click.argument("raqam", type=int)
def bajar(raqam):
    """Vazifani bajarildi deb belgilaydi."""
    if 1 <= raqam <= len(VAZIFALAR):
        VAZIFALAR[raqam - 1]["bajarildi"] = True
        click.echo(f"Bajarildi: {VAZIFALAR[raqam - 1]['matn']}")
    else:
        click.echo(f"Xato: {raqam}-vazifa yo'q", err=True)
        raise click.exceptions.Exit(1)


def main() -> None:
    runner = CliRunner()

    print("=== 1. Vazifalar qo'shish ===")
    for chaqiruv in [["qosh", "16-qismni yozish"], ["qosh", "Testlarni o'tkazish", "--muhim"]]:
        natija = runner.invoke(cli, chaqiruv)
        print(f"  {natija.output.strip()}")

    print("\n=== 2. Ro'yxat ===")
    natija = runner.invoke(cli, ["royxat"])
    for qator in natija.output.splitlines():
        print(f"  {qator}")

    print("\n=== 3. Vazifani bajarish ===")
    natija = runner.invoke(cli, ["bajar", "1"])
    print(f"  {natija.output.strip()}")
    natija = runner.invoke(cli, ["royxat"])
    for qator in natija.output.splitlines():
        print(f"  {qator}")

    print("\n=== 4. Xato holati (chiqish kodi) ===")
    natija = runner.invoke(cli, ["bajar", "99"])
    print(f"  exit_code: {natija.exit_code} (0 emas — xato)")
    print(f"  xato xabari: {natija.output.strip()}")

    print("\n=== 5. [project.scripts] integratsiyasi ===")
    print("  pyproject.toml: [project.scripts]")
    print('                  wisar = "wisar.cli:cli"')
    print("  o'rnatilgach: wisar qosh 'yangi vazifa' --muhim")
    print("  ⭐ CLI terminal buyrug'iga aylanadi 19.2-bob")


if __name__ == "__main__":
    main()

Natijaning muhim qismi:

text
=== 1. Vazifalar qo'shish ===
  Qo'shildi: 16-qismni yozish
  Qo'shildi: Testlarni o'tkazish (muhim)

=== 2. Ro'yxat ===
  [ ]  1. 16-qismni yozish
  [ ]! 2. Testlarni o'tkazish

=== 3. Vazifani bajarish ===
  Bajarildi: 16-qismni yozish
  [✓]  1. 16-qismni yozish
  [ ]! 2. Testlarni o'tkazish

=== 4. Xato holati (chiqish kodi) ===
  exit_code: 1 (0 emas — xato)
  xato xabari: Xato: 99-vazifa yo'q

=== 5. [project.scripts] integratsiyasi ===
  pyproject.toml: [project.scripts]
                  wisar = "wisar.cli:cli"
  o'rnatilgach: wisar qosh 'yangi vazifa' --muhim
  ⭐ CLI terminal buyrug'iga aylanadi (19.2)

Nima ko'rsatdi: 2.5, 2.6, 2.7, 2.8-bo'limlar.


5. To'g'ri va noto'g'ri tushunishlar

Noto'g'ri fikr To'g'risi
"sys.argv ni qo'lda o'qish yetarli" argparse yordam, xato, turlarni beradi
"Yordam matnini qo'lda yozish kerak" Avtomatik yaratiladi
"CLI ni test qilib bo'lmaydi" CliRunner / parse_args bilan
"argparse va click bir xil" click ergonomikroq (dekoratorlar)
"Chiqish kodi arzimas" 0/1 — CI va skriptlar uchun muhim
"Xato stdout ga" Xato stderr ga, natija stdout ga
"CLI = python skript.py" [project.scripts] bilan buyruq
"Bayroqqa qiymat kerak" store_true/is_flag — qiymatsiz

6. Keng tarqalgan xatolar va yechimlari

1. sys.argv ni qo'lda o'qish

python
ism = sys.argv[1]                          # ❌ yordam yo'q, xato noaniq
parser.add_argument("ism")                 # ✅ argparse

2. Yordam yozmaslik

python
parser.add_argument("ism")                 # ⚠️ help yo'q
parser.add_argument("ism", help="...")     # ✅

3. Turni tekshirmaslik

python
necha = int(sys.argv[2])                    # ❌ noto'g'ri turda yiqiladi
parser.add_argument("--necha", type=int)   # ✅ argparse tekshiradi

4. Xatoni stdout ga

python
print("Xato: ...")                         # ❌ natija bilan aralashadi
print("Xato: ...", file=sys.stderr)        # ✅ stderr
click.echo("Xato", err=True)               # ✅ click

5. Chiqish kodini bermaslik

python
# xato bo'lsa ham 0 qaytarish                # ❌ CI tushunmaydi
sys.exit(1)                                # ✅ xato uchun 1

6. CLI ni test qilmaslik

python
# faqat qo'lda sinash                        # ❌
CliRunner().invoke(cli, [...])             # ✅ avtomatik test

7. [project.scripts] siz

bash
python -m wisar.cli salom Aziz             # ⚠️ uzun
wisar salom Aziz                           # ✅ [project.scripts] bilan

7. Integratsiya — bu bilim qayerda kerak bo'ladi

  • 15.15-dars (o'tilgan): argparse CLI — bu yerda paketlashda
  • 19.2-dars (o'tilgan): [project.scripts] — buyruq yaratish
  • 17-qism (o'tilgan): testlar — CliRunner bilan CLI test
  • 16.8-dars (o'tilgan): oqim — katta CLI chiqishda
  • 26-qism: avtomatlashtirish — CLI vositalar

8. Eng yaxshi amaliyotlar

  1. argparse (stdlib) yoki click (qulay) ishlating, sys.argv emas.

  2. Har argumentga help yozing — avtomatik yordam.

  3. type= bilan turlarni tekshiring.

  4. Murakkab CLI ni ost-buyruqlarga bo'ling.

  5. CLI ni test qiling (CliRunner/parse_args).

  6. Xato — stderr ga, natija — stdout ga; chiqish kodi 0/1.

  7. [project.scripts] bilan terminal buyrug'i yarating.

  8. Standart konvensiyalar (-h, --version, -v).


9. Amaliy topshiriq

Vazifa 1: Bashorat qiling

python
1.  # pozitsion argument majburmi?
2.  # --katta store_true nima qiladi?
3.  # type=int nima tekshiradi?
4.  # --help kim yaratadi?
5.  # ost-buyruq qanday qo'shiladi?
6.  # click qanday CLI quradi?
7.  # CliRunner nima uchun?
8.  # xato qayerga (stdout/stderr)?
9.  # muvaffaqiyat chiqish kodi?
10. # [project.scripts] nima yaratadi?
11. # is_flag click da nima?
12. # argparse yoki click qulayroq?
Javoblar
  1. Ha (pozitsion — majburiy)
  2. Bayroq: bor→True, yo'q→False
  3. Argument butun son ekanini
  4. argparse/click avtomatik
  5. add_subparsers / @click.group
  6. Dekoratorlar bilan
  7. CLI ni dasturiy test qilish
  8. stderr ga (natija stdout)
  9. 0
  10. Terminal buyrug'i
  11. Bayroq (store_true kabi)
  12. click (dekoratorlar, ergonomik)

Vazifa 2: Xatolarni tuzating

python
1.  import sys
    ism = sys.argv[1]
    necha = int(sys.argv[2])

2.  parser.add_argument("ism")      # help yo'q

3.  parser.add_argument("--necha")  # type yo'q
    necha = args.necha + 1          # str + int

4.  print("Xato: fayl topilmadi")   # stdout ga

5.  # xato bo'lsa ham:
    return                          # chiqish kodi 0
Javoblar
python
1.  parser = argparse.ArgumentParser()
    parser.add_argument("ism")
    parser.add_argument("necha", type=int)
    args = parser.parse_args()

2.  parser.add_argument("ism", help="foydalanuvchi ismi")

3.  parser.add_argument("--necha", type=int, default=1)
    necha = args.necha + 1

4.  print("Xato: fayl topilmadi", file=sys.stderr)

5.  sys.exit(1)                     # xato uchun 1

Vazifa 3: Kalkulyator CLI

argparse bilan:

  1. Ost-buyruqlar: qosh, ayir, kopaytir, bol
  2. Ikki son argumenti
  3. --verbose bayrog'i (batafsil chiqish)
  4. Nolga bo'lish xatosi (stderr, chiqish kodi 1)

Vazifa 4: click bilan qayta yozish

3-vazifadagi kalkulyatorni click bilan:

  1. @click.group va buyruqlar
  2. CliRunner bilan test
  3. Docstring dan yordam
  4. argparse bilan solishtiring

Vazifa 5: Fayl vositasi

Fayl bilan ishlaydigan CLI (sanash, qidir, almashtir):

  1. Fayl argumenti va tekshiruvi
  2. Oqim bilan o'qish (16.8)
  3. Chiqish kodlari (topildi/topilmadi)
  4. --help va testlar

Vazifa 6: --version va konvensiyalar

  1. --version bayrog'i (__version__ dan)
  2. -v/--verbose darajalari
  3. -q/--quiet rejimi
  4. Standart konvensiyalarni qo'llang

Vazifa 7: O'ylash

CLI 1970-yillardan beri mavjud (Unix), lekin grafik interfeyslar (GUI) davrida ham dasturchilar orasida hukmron bo'lib qolmoqda — git, docker, kubectl hammasi CLI. Nima uchun CLI dasturchilar uchun bunday afzal, va u qanday tamoyillar (kompozitsiya, avtomatlashtirish) tufayli GUI dan ustun turadi?

Javob

Qisqa javob: CLI dasturchilar uchun afzal, chunki u kompozitsiya va avtomatlashtirish ga imkon beradi: CLI buyruqlarini birlashtirish (|, &&), skriptlarga joylash, takrorlash mumkin — GUI da har amal qo'lda bosishni talab qiladi. CLI matnga asoslangan (bosh, dumaloq emas): matn yoziladi, saqlanadi, versiyalanadi, uzatiladi. Bu Unix falsafasi — "kichik vositalar, bittasi bir ishni yaxshi qiladi, ular birlashtiriladi".

1. Nega CLI afzal

Sabab Tafsilot
Avtomatlashtirish Skriptga joylash, takrorlash
Kompozitsiya Buyruqlarni birlashtirish (|)
Tez Klaviaturadan, sichqonchasiz
Uzoq boshqaruv Server (SSH) da GUI yo'q
Versiyalanadi Buyruqlar matn — git'da
Aniqlik Aynan nima bajarilganini yozib olish

2. Unix falsafasi

Tamoyil Tafsilot
Kichik vositalar Bittasi bir ishni yaxshi
Matn oqimi Universal interfeys
Kompozitsiya Vositalarni birlashtirish
Avtomatlashtirish Skriptlar

3. CLI vs GUI

CLI GUI
Avtomatlashtiriladi Qo'lda bosish
Birlashtiriladi Alohida
Skriptlanadi Yo'q
Tez (tajribali) Oson (yangi)
Uzoqdan Mahalliy

4. Nima uchun hukmron qoladi

Dasturchi ishi takrorlanuvchi va avtomatlashtiriladigan: qurish, test, deploy. CLI bularni skriptga aylantiradi. GUI bir martalik ish uchun yaxshi, lekin takrorlanuvchi ish uchun CLI ustun.

5. Muhandislik saboqlari

  1. Matn interfeysi — kompozitsiya va avtomatlashtirish
  2. Kichik, birlashtiriladigan vositalar (Unix)
  3. Avtomatlashtirish — mahsuldorlik
  4. CLI va GUI — turli maqsad uchun

6. Xulosa

  1. CLI kompozitsiya va avtomatlashtirishga imkon beradi
  2. Matn — versiyalanadi, uzatiladi, skriptlanadi
  3. Unix falsafasi: kichik, birlashtiriladigan vositalar
  4. Takrorlanuvchi dasturchi ishi uchun CLI ustun

Nimani mustahkamlaydi: 2.1–2.8-bo'limlar.


Xulosa

Bu darsda CLI dastur yaratishni o'rgandik.

Eng muhim uch fikr:

  1. argparse — argumentlar, yordam, xatolarni avtomatlashtiradi. sys.argv ni qo'lda o'qish o'rniga argparse (stdlib) parser yaratadi: pozitsion argumentlar (majburiy), ixtiyoriy (--necha 3), bayroqlar (--katta, store_true). type=int turlarni tekshiradi, --help avtomatik yordam beradi, noto'g'ri argument aniq xato ko'rsatadi. Murakkab CLI (git commit kabi) add_subparsers bilan ost-buyruqlarga bo'linadi.

  2. click — ergonomikroq alternativa. click (tashqi) CLI ni dekoratorlar bilan quradi: @click.command(), @click.argument(), @click.option(). Docstring avtomatik yordamga aylanadi, is_flag bayroq beradi, @click.group() ost-buyruqlar. CLI ham test qilinadi (17-qism): click.testing.CliRunner CLI ni dasturiy ishga tushirib exit_code va output ni tekshiradi.

  3. [project.scripts] va yaxshi dizayn. [project.scripts] 19.2-bob CLI funksiyani terminal buyrug'iga bog'laydi (wisar = "wisar.cli:cli"): o'rnatilgach wisar salom Aziz deb ishlatiladi. Yaxshi CLI: har buyruqda aniq yordam, mos chiqish kodlari (0 — muvaffaqiyat, 0 emas — xato), xato stderr ga (natija stdout ga), standart konvensiyalar (-h, --version). CLI kompozitsiya va avtomatlashtirishga imkon bergani uchun dasturchilar orasida hukmron.

Keyingi darsda kodni hujjatlashni o'rganamiz: Sphinx va MkDocs bilan professional hujjatlar yaratish, docstring lar va API hujjatlarini avtomatik generatsiya qilish.

Ulashish:Telegram'da

Izohlar (0)

Izoh yozish uchun kiring.

  • Hozircha izoh yo'q. Birinchi bo'ling!
19.6-dars: CLI dastur yaratish — IlmHamroh