Particionált üzenetsorok és témakörök

Az Azure Service Bus több üzenetközvetítőt használ az üzenetek feldolgozásához, és több üzenettárolót is használ az üzenetek tárolásához. A hagyományos üzenetsorokat vagy témaköröket egyetlen üzenetközvetítő kezeli, és egyetlen üzenettárolóban tárolja. A Service Bus-partíciók lehetővé teszik az üzenetsorok és témakörök, illetve üzenetkezelési entitások particionálását több üzenetközvetítő és üzenetkezelő tároló között. A particionálás azt jelenti, hogy a particionált entitások teljes átviteli sebességét már nem korlátozza egyetlen üzenetközvetítő vagy üzenettároló teljesítménye. Ezenkívül az üzenettár ideiglenes kimaradása nem teszi elérhetetlenné a particionált üzenetsort vagy témakört. A particionált üzenetsorok és témakörök tartalmazhatnak minden speciális Service Bus-funkciót, például a tranzakciók és munkamenetek támogatását.

Feljegyzés

A particionálás terén van néhány különbség az alapszintű/ standard és a prémium termékváltozat között.

  • A particionálás az entitáslétrehozáskor érhető el az alapszintű vagy standard termékváltozatok összes üzenetsorához és témaköréhez. A névterek particionált és nem particionált entitásokkal is rendelkezhetnek.
  • A particionálás a prémium szintű üzenetkezelési termékváltozat névtér-létrehozásakor érhető el, és a névtér összes üzenetsora és témaköre particionálásra kerül. A Prémium névterekben korábban migrált particionált entitások továbbra is a várt módon működnek.
  • Ha a particionálás engedélyezve van az alapszintű vagy standard termékváltozatokban, mindig 16 partíciót hozunk létre.
  • Ha a particionálás engedélyezve van a Prémium termékváltozatban, a rendszer a névtér létrehozásakor adja meg a partíciók mennyiségét.

A particionálási beállítás nem módosítható meglévő névtéren, üzenetsoron vagy témakörben; ezt a beállítást csak az entitás létrehozásakor állíthatja be.

Működés

Minden particionált üzenetsor vagy témakör több partícióból áll. Minden partíció egy másik üzenettárban van tárolva, és egy másik üzenetközvetítő kezeli. Ha egy üzenet particionált üzenetsorba vagy témakörbe kerül, a Service Bus hozzárendeli az üzenetet az egyik partícióhoz. A kiválasztást a Service Bus véletlenszerűen vagy a feladó által megadható partíciókulcs használatával végzi.

Ha egy ügyfél egy particionált üzenetsorból vagy egy particionált témakörre szóló előfizetésből szeretne üzenetet kapni, a Service Bus lekérdezi az összes partíciót az üzenetekhez, majd visszaadja az első üzenetet, amelyet bármelyik üzenettárolóból lekér a fogadónak. A Service Bus gyorsítótárazza a többi üzenetet, és visszaadja őket, amikor több fogadási kérést kap. A fogadó ügyfél nem ismeri a particionálást; a particionált üzenetsorok vagy témakörök ügyféloldali viselkedése (például olvasás, kiegészítés, halasztás, holtpont, előkezelés) megegyezik a normál entitás viselkedésével.

A nem particionált entitások betekintő művelete mindig a legrégebbi üzenetet adja vissza, particionált entitáson azonban nem. Ehelyett az egyik partíció legrégebbi üzenetét adja vissza, amelynek üzenetközvetítője válaszolt először. Nincs garancia arra, hogy a visszaadott üzenet a legrégebbi az összes partíción.

A particionált üzenetsorba vagy témakörbe küldött üzenetek vagy témakörök nem járnak többletköltséggel.

Feljegyzés

A betekintő művelet a partíció legrégebbi üzenetét adja vissza a sorszáma alapján. Particionált entitások esetén a rendszer a partícióhoz viszonyítva adja ki a sorszámot. További információ: Üzenetszekvenálás és időbélyegek.

Partíciókulcsok használata

Ha egy üzenet particionált üzenetsorba vagy témakörbe van beolvasva, a Service Bus ellenőrzi, hogy van-e partíciókulcs. Ha talál egyet, a kulcs alapján választja ki a partíciót. Ha nem talál partíciókulcsot, egy belső algoritmus alapján választja ki a partíciót.

Partíciókulcs használata

Egyes forgatókönyvek, például munkamenetek vagy tranzakciók esetében az üzeneteket egy adott partíción kell tárolni. Ezekhez a forgatókönyvekhez partíciókulcsot kell használni. Az azonos partíciókulcsot használó összes üzenet ugyanahhoz a partícióhoz van rendelve. Ha a partíció átmenetileg nem érhető el, a Service Bus hibát ad vissza.

A forgatókönyvtől függően a rendszer különböző üzenettulajdonságokat használ partíciókulcsként:

SessionId: Ha egy üzenet rendelkezik a munkamenet-azonosító tulajdonságával, akkor a Service Bus partíciókulcsként használja. Így az ugyanahhoz a munkamenethez tartozó összes üzenetet ugyanaz az üzenetközvetítő kezeli. A munkamenetek lehetővé teszik, hogy a Service Bus garantálja az üzenetek sorrendjét és a munkamenet-állapotok konzisztenciáját.

PartitionKey: Ha egy üzenet rendelkezik a partíciókulcs tulajdonságával, de a munkamenet-azonosító tulajdonsága nem, akkor a Service Bus a partíciókulcs tulajdonságértékét használja partíciókulcsként. Ha az üzenetben a munkamenet-azonosító és a partíciókulcs tulajdonságai is meg vannak adva, mindkét tulajdonságnak azonosnak kell lennie. Ha a partíciókulcs tulajdonsága a munkamenet-azonosító tulajdonságtól eltérő értékre van beállítva, a Service Bus érvénytelen műveletkivételt ad vissza. A partíciókulcs tulajdonságot akkor kell használni, ha a feladó nem ad meg a tranzakcióval kapcsolatos üzeneteket. A partíciókulcs biztosítja, hogy a tranzakción belül küldött összes üzenetet ugyanaz az üzenetközvetítő kezelje.

MessageId: Ha az üzenetsort vagy témakört az ismétlődő észlelési funkcióval hozták létre, és a munkamenet-azonosító vagy a partíciókulcs tulajdonságai nincsenek beállítva, akkor az üzenetazonosító tulajdonság értéke partíciókulcsként szolgál. (A Microsoft ügyfélkódtárai automatikusan hozzárendelnek egy üzenetazonosítót, ha a küldő alkalmazás nem.) Ebben az esetben ugyanannak az üzenetnek az összes példányát ugyanaz az üzenetközvetítő kezeli. Ez az azonosító lehetővé teszi, hogy a Service Bus észlelje és kiküszöbölje az ismétlődő üzeneteket. Ha az ismétlődő észlelési funkció nincs engedélyezve, a Service Bus nem tekinti az üzenetazonosító tulajdonságot partíciókulcsnak.

Partíciókulcs használata nem

Partíciókulcs hiányában a Service Bus ciklikus időszeleteléses módon osztja el az üzeneteket a particionált üzenetsor vagy témakör összes partíciójára. Ha a kiválasztott partíció nem érhető el, a Service Bus egy másik partícióhoz rendeli az üzenetet. Így a küldési művelet az üzenettár ideiglenes elérhetetlensége ellenére is sikeres lesz. A partíciókulcsok által biztosított garantált sorrend azonban nem érhető el.

A rendelkezésre állás (partíciókulcs nélkül) és a konzisztencia (partíciókulcs használata) közötti kompromisszum részletesebb ismertetéséhez tekintse meg az Event Hubs rendelkezésre állását és konzisztenciáját. A particionált Service Bus-entitásokra a partícióazonosító felhasználók számára való nem való felfedése kivételével ez az információ egyformán érvényes.

Ahhoz, hogy a Service Bus elegendő időt adjon az üzenet egy másik partícióba való beolvasásához, az üzenetet küldő ügyfél által megadott időtúllépési értéknek 15 másodpercnél hosszabbnak kell lennie. Az alapértelmezett érték 60 másodperc.

A partíciókulcs "rögzít" egy üzenetet egy adott partícióra. Ha a partíciót tartalmazó üzenettár nem érhető el, a Service Bus hibát ad vissza. Partíciókulcs hiányában a Service Bus választhat egy másik partíciót, és a művelet sikeres lesz. Ezért javasoljuk, hogy csak akkor adjon meg partíciókulcsot, ha szükséges.

Speciális témakörök

Tranzakciók használata particionált entitásokkal

A tranzakciók keretében küldött üzenetekben meg kell adni egy partíciókulcsot. A kulcs a következő tulajdonságok egyike lehet: munkamenet-azonosító, partíciókulcs vagy üzenetazonosító. Az ugyanazon tranzakció részeként küldött összes üzenetnek ugyanazt a partíciókulcsot kell megadnia. Ha egy tranzakción belül partíciókulcs nélkül próbál üzenetet küldeni, a Service Bus érvénytelen műveletkivételt ad vissza. Ha több üzenetet próbál elküldeni ugyanazon a tranzakción belül, amely különböző partíciókulcsokkal rendelkezik, a Service Bus érvénytelen műveletkivételt ad vissza. Példa:

CommittableTransaction committableTransaction = new CommittableTransaction();
using (TransactionScope ts = new TransactionScope(committableTransaction))
{
    ServiceBusMessage msg = new ServiceBusMessage("This is a message");
    msg.PartitionKey = "myPartitionKey";
    await sender.SendMessageAsync(msg); 
    ts.Complete();
}
committableTransaction.Commit();

Ha a partíciókulcsként szolgáló tulajdonságok bármelyike be van állítva, a Service Bus egy adott partícióra rögzíti az üzenetet. Ez a viselkedés akkor fordul elő, ha tranzakciót használ. Javasoljuk, hogy ne adjon meg partíciókulcsot, ha nincs rá szükség.

Tranzakciók használata particionált entitásokkal rendelkező munkamenetekben

Ha tranzakciós üzenetet szeretne küldeni egy munkamenet-tudatos témakörbe vagy üzenetsorba, az üzenetnek rendelkeznie kell a munkamenet-azonosító tulajdonságával. Ha a partíciókulcs tulajdonság is meg van adva, annak meg kell egyeznie a munkamenet-azonosító tulajdonságával. Ha eltérnek, a Service Bus érvénytelen műveleti kivételt ad vissza.

A normál (nem particionált) üzenetsorokkal vagy témakörökkel ellentétben egyetlen tranzakcióval nem lehet több üzenetet küldeni különböző munkamenetekbe. Ha megkísérlik, a Service Bus érvénytelen műveletkivételt ad vissza. Példa:

CommittableTransaction committableTransaction = new CommittableTransaction();
using (TransactionScope ts = new TransactionScope(committableTransaction))
{
    ServiceBusMessage msg = new ServiceBusMessage("This is a message");
    msg.SessionId = "mySession";
    await sender.SendMessageAsync(msg); 
    ts.Complete();
}
committableTransaction.Commit();

Automatikus üzenettovábbítás particionált entitásokkal

A Service Bus támogatja a particionált entitások közötti automatikus üzenettovábbítást. Ezt a funkciót az üzenetsorok és előfizetések létrehozásakor vagy frissítésekor is engedélyezheti. További információ: Üzenettovábbítás engedélyezése. Ha az üzenet egy partíciókulcsot (munkamenet-azonosítót, partíciókulcsot vagy üzenetazonosítót) ad meg, akkor a rendszer ezt a partíciókulcsot használja a célentitáshoz.

Megfontolandó szempontok és irányelvek

  • Magas konzisztencia-funkciók: Ha egy entitás olyan funkciókat használ, mint a munkamenetek, a duplikált észlelés vagy a particionálási kulcs explicit vezérlése, akkor az üzenetkezelési műveletek mindig adott partícióra lesznek irányítva. Ha bármelyik partíció nagy forgalmat tapasztal, vagy a mögöttes tároló nem megfelelő, ezek a műveletek meghiúsulnak, és a rendelkezésre állás csökken. Összességében a konzisztencia még mindig sokkal magasabb, mint a nem particionált entitások; csak a forgalom egy részhalmaza tapasztal problémákat, szemben az összes forgalommal. További információkért tekintse meg a rendelkezésre állásról és a konzisztenciáról szóló vitafórumot.
  • Felügyelet: Az olyan műveleteket, mint a létrehozás, a frissítés és a törlés, az entitás összes partícióján el kell végezni. Ha bármelyik partíció nem megfelelő, az ezekhez a műveletekhez hibákhoz vezethet. A Lekérés művelethez az olyan információkat, mint az üzenetszám, összesíteni kell az összes partícióból. Ha bármelyik partíció nem megfelelő, az entitás rendelkezésre állási állapota korlátozottként lesz jelentve.
  • Alacsony kötetű üzenetforgatókönyvek: Ilyen helyzetekben, különösen a HTTP protokoll használatakor előfordulhat, hogy több fogadási műveletet kell végrehajtania az összes üzenet beszerzéséhez. Fogadási kérések esetén az előtér minden partíción fogad, és gyorsítótárazza az összes kapott választ. Az ugyanazon a kapcsolaton alapuló későbbi fogadási kérések kihasználnák ezt a gyorsítótárazást, és alacsonyabbak a késések. Ha azonban több kapcsolattal rendelkezik, vagy HTTP-t használ, minden kéréshez új kapcsolat jön létre. Így nincs garancia arra, hogy ugyanazon a csomóponton fog leszállni. Ha az összes meglévő üzenet zárolva van és gyorsítótárazva van egy másik előtérben, a fogadási művelet null értéket ad vissza. Az üzenetek végül lejárnak, és újra megkaphatja őket. A HTTP életben tartása ajánlott. Ha particionálást használ alacsony kötetű forgatókönyvekben, a fogadási műveletek a vártnál tovább tarthatnak. Ezért javasoljuk, hogy ezekben a forgatókönyvekben ne használjon particionálást. Törölje a meglévő particionált entitásokat, és hozza létre őket a teljesítmény javítása érdekében letiltott particionálással.
  • Tallózás/Betekintő üzenetek: A betekintő művelet nem mindig adja vissza a kért üzenetek számát. Ennek a viselkedésnek két gyakori oka van. Ennek egyik oka, hogy az üzenetgyűjtemény összesített mérete meghaladja a maximális méretet. A másik ok az, hogy a particionált üzenetsorokban vagy témakörökben előfordulhat, hogy a partíciók nem rendelkeznek elegendő üzenettel a kért számú üzenet visszaadásához. Általánosságban elmondható, hogy ha egy alkalmazás egy adott számú üzenetet szeretne betekinteni/tallózni, a betekintő műveletet többször kell meghívnia, amíg meg nem kapja az adott számú üzenetet, vagy nincs több betekintendő üzenet. További információ, beleértve a kódmintákat, lásd : Üzenetböngészés.

Particionált entitások korlátozásai

A Service Bus jelenleg a következő korlátozásokat szabja meg a particionált üzenetsorokra és témakörökre:

  • Particionált prémium szintű névterek esetén az üzenet mérete 1 MB-ra korlátozódik, amikor az üzeneteket egyenként küldi el, és a köteg mérete 1 MB-ra korlátozódik, amikor az üzeneteket kötegben küldi el.
  • A particionált üzenetsorok és témakörök nem támogatják az egyetlen tranzakció különböző munkameneteihez tartozó üzenetek küldését.
  • A Service Bus jelenleg legfeljebb 100 particionált üzenetsort vagy témakört engedélyez névtérenként az Alapszintű és a Standard termékváltozathoz. Minden particionált üzenetsor vagy témakör névtérenként 10 000 entitás kvótájának számít.

Következő lépések

A particionálást az Azure Portal, a PowerShell, a parancssori felület, a Resource Manager-sablon, a .NET, a Java, a Python és a JavaScript használatával engedélyezheti. További információ: Particionálás engedélyezése (Alapszintű / Standard).

Az Advanced Message Queueing Protocol (AMQP) 1.0 üzenetkezelési specifikáció alapfogalmait az AMQP 1.0 protokoll útmutatójában találja.