Ձեր հավելվածը շարունակում է աշխատել, մինչ տունելը մահանում է։ Wi-Fi-ը դեռ միացած է, ինտերնետը դեռ պատասխանում է, և այն մասնավոր API-ն, որից կախված է հավելվածը, դարձել է անհասանելի։ .NET իրադարձությունը, որին մարդիկ սովորաբար դիմում են այստեղ, NetworkAvailabilityChanged ընդհանրապես չի նկարագրում այդ իրավիճակը։ Այն հաղորդում է մեքենայի ընդհանուր վիճակի փոփոխության մասին, և այդ վիճակը կարող է ճշմարիտ մնալ VPN-ի անջատման և վերամիացման ընթացքում։ Դիտարկիչը պետք է հետևի տունելը տիրապետող կլիենտին, ոչ թե ցանցային շերտի ամփոփմանը։

Հասանելիությունը համախմբված ցուցանիշ է, ոչ ձեր տունելը

NetworkAvailabilityChanged գործարկվում է, երբ փոխվում է մեքենայի հասանելիության համախմբված պատասխանը, և այդ պատասխանը հաշվում է ցանկացած ակտիվ ինտերֆեյս, բացի loopback-ից կամ տունելից։

Wi-Fi-ի ակտիվ ժամանակ VPN-ի անկումը ոչինչ չի փոխում նրանում, ինչ նա չափում է, դրա համար էլ իրադարձությունը կարող է լուռ մնալ հենց այն խափանման ընթացքում, որ ձեզ հետաքրքրում է։

Վիճակի հոսքը պատկանում է տունելը տիրապետող կլիենտին

Որոշեք, թե որ բաղադրիչն է տիրապետում միացմանը՝ OpenVPN GUI-ն կամ ծառայությունը, OpenVPN Connect-ը, թե գործընթաց, որը ձեր հավելվածը գործարկել և կառավարում է։ Սրանք տարբեր տերեր են՝ տարբեր աջակցվող ինտերֆեյսներով, և դիտարկիչը պետք է օգտագործի տեղակայմանը համապատասխանը։ OpenVPN գործընթացի համար, որի հետ ձեզ թույլատրված է ինտեգրվել, կառավարման ինտերֆեյսը հաղորդում է ընթացիկ վիճակը, պատմությունը և իրական ժամանակի ծանուցումները։ Վերլուծեք փաստաթղթավորված կառուցվածքային հաղորդագրությունները՝ տեղայնացված GUI վերնագրում connected բառը փնտրելու փոխարեն։

Կառավարման ալիքը արտոնյալ կառավարման մակերես է, այնպես որ նոր լսող չբացեք և չվիճեք GUI-ի հետ ալիքի համար, որն արդեն նրա ձեռքում է։

Սերնդային պահակները կանգնեցնում են հնացած արդյունքները

Յուրաքանչյուր դիտարկում պատկանում է կոնկրետ միացման փորձի։ Ավելացրեք սերնդի հաշվիչը, երբ սկսվում է նոր փորձ, երբ կորչում է ալիքը և երբ կլիենտը հաղորդում է ելքի մասին։

Դիտարկենք մի ստուգում, որը սկսվել է A միացման ընթացքում։ Տունելը ընկնում է, սկսվում է B միացումը, և հետո գալիս է A-ի ուշացած HTTP հաջողությունը։ Առանց պահակի այդ հին արդյունքը ցուցադրությունը կանաչ է դարձնում, մինչ B-ն դեռ նույնականացվում է։ Չեղարկումը նվազեցնում է վատնված աշխատանքը, և սերնդի ստուգումն է, որ թույլ չի տալիս հնացած ավարտին դառնալ ընթացիկ վիճակ:

var generation = _generation;
var reachable = await ProbeAsync(token);
if (generation != _generation) return;
Publish(reachable);

Նույն կանոնը կիրառեք UI-ի ուղարկման շուրջ, որովհետև մարշալված թարմացումը կարող է հասնել այն բանից հետո, երբ սերունդն առաջ է գնացել։

Նախաձեռնումը և վերամիացումը մեկ կենսացիկլ են

Առաջին միացումը, վերամիացումը և ալիքի կորուստը դիտեք որպես մեկ կենսացիկլ՝ մեկ կանոնների հավաքածուով:

  • Կարդացեք ընթացիկ վիճակը և բաժանորդագրվեք ծանուցումներին մեկ քայլով, որտեղ ինտերֆեյսը դա թույլ է տալիս։
  • Յուրաքանչյուր դիտարկում նշեք միացման ինքնությամբ և սերնդով։
  • Անվավերացրեք պատրաստականությունը վերամիացման, ելքի կամ կորած դիտարկման ալիքի դեպքում։
  • Ստուգեք մասնավոր ռեսուրսը միայն այն բանից հետո, երբ տերը հաղորդի նախաձեռնման ավարտի մասին։
  • Հրապարակեք միայն այն արդյունքները, որոնք դեռ պատկանում են ընթացիկ սերնդին։

Կորած ալիքը նշանակում է անհայտ, ոչ թե անջատված։ Անհայտի մասին հաղորդելը ավելի ազնիվ է, քան անջատման մասին հաղորդելը, որն անհնար է ապացուցել, և դա թույլ չի տալիս կրկնափորձի տրամաբանությանը գործել ենթադրության հիման վրա։

Հաղորդեք ապացույցներ, ոչ թե բուլյան արժեք

Վերադարձրեք անվանված սեսիայի վիճակը և ռեսուրսի պատրաստականությունը որպես առանձին արժեքներ՝ յուրաքանչյուրը տարիքով։ Որոշում կայացնող սպառողը կարող է տեսնել, որ վերջին հաջող ստուգումը քառասուն վայրկյան հնություն ունի, ինչը տարբեր տեղեկություն է թարմից։

Հանրային IP-ի որոնումը ապացույց չէ, որ մասնավոր API-ն օգտագործել է պահանջվող երթուղին, այնպես որ մի ներկայացրեք այն այդպես։

Կատարումը պահեք դիտարկիչից դուրս

Հետկանչը գործարկվում է փաստից հետո։ Այն չի կարող երաշխավորել, որ իրադարձության և մշակիչի միջև ոչ մի փաթեթ չի լքել մեքենան։ Եթե դիզայնը պահանջում է արգելափակում, այն պետք է ապահովի ցանցային քաղաքականությունը, և դիտարկիչի խնդիրն է բացատրել ապացույցները կանչողին։ Երկուսը խառնելը ստեղծում է կոդ, որը իրեն հրային պատ է համարում, որովհետև բուլյան արժեք է պահում։ Կատարման շերտը պահեք ձանձրալի և փորձարկելի, և թույլ տվեք դիտարկիչին մնալ ընթերցող։

Այնուհետև UI-ի հարցը դառնում է պարզ՝ ցույց տվեք, ինչ հայտնի է, իր տարիքով, և ասացեք անհայտ, երբ այդպես է։

Առնչվող հոդվածներ