Bonjour is een technologie die het ontdekken van services heel eenvoudig maakt. Ondanks de kracht en het gebruiksgemak krijgt het niet veel aandacht in de Cocoa-gemeenschap. Bonjour werkt heel goed met de CocoaAsyncSocket-bibliotheek, een open-sourcebibliotheek die een Objective-C-interface biedt voor het werken met sockets op iOS en OS X. In deze serie zal ik u kennis laten maken met Bonjour en de CocoaAsyncSocket-bibliotheek door een eenvoudige, netwerkspel. Onderweg zal ik je inleiden in de wereld van netwerken door de TCP- en UDP-protocollen te bespreken, evenals sockets, streams en poorten!
In deze serie zullen we een eenvoudig genetwerkt spel maken. Onze primaire focus zal het netwerkaspect van het spel zijn. Ik zal je laten zien hoe je twee apparaten kunt verbinden met Bonjour en de krachtige CocoaAsyncSocket-bibliotheek. De game die we gaan maken, stelt twee mensen op hetzelfde netwerk in staat om elkaar uit te dagen. De game zelf zal niet erg geavanceerd zijn, dus verwacht geen grafisch rijke FPS.
In deze serie zal ik niet praten over de infrastructuur waarmee netwerktoepassingen met elkaar kunnen communiceren. In plaats daarvan zal ik me concentreren op de protocollen en technologieën die de basis vormen voor netwerktoepassingen. Een basiskennis van de TCP- en UDP-protocollen, sockets en streams is van onschatbare waarde voor elke ontwikkelaar, met name degenen die van plan zijn om applicaties te maken die afhankelijk zijn van netwerkconnectiviteit. Zelfs als je Bonjour niet wilt gebruiken, raad ik je aan de rest van dit artikel te lezen om meer inzicht te krijgen in netwerken.
In dit artikel zoom ik in op verschillende belangrijke componenten van netwerktoepassingen. Het zal je helpen te begrijpen hoe Bonjour werkt, wat Bonjour is (en is dat niet), en het zal ook het werken met de CocoaAsyncSocket-bibliotheek veel gemakkelijker maken.
Houd er rekening mee dat Bonjour geen genetwerkte toepassing hoeft te ontwikkelen. De meeste op Unix gebaseerde besturingssystemen, zoals iOS en OS X, gebruiken BSD-sockets als hun fundamentele netwerkprogrammeringsinterface. Op iOS en OS X is de BSD socketbibliotheek direct beschikbaar. Het werken met de BSD Socket-bibliotheek is echter niet voor bangeriken en vereist een grondige kennis van socketprogrammering en de C-taal. Op iOS en OS X kunt u ook gebruik maken van het lage niveau CFNetwork framework, dat een directe uitbreiding is op BSD-sockets. Apple ontwierp het CFNetwork-raamwerk om netwerken gemakkelijker te maken door directe interactie met BSD-sockets te vermijden. Een van de belangrijkste voordelen van CFNetwork is de ingebouwde ondersteuning voor run-loop-integratie. CFNetwork maakt deel uit van het Core Foundation-raamwerk en is geschreven in C.
Een verrassend aantal iOS- en OS X-ontwikkelaars is zo gewend aan de Objective-C-syntaxis dat ze schrikken van bibliotheken en frameworks die zijn geschreven in C. Als je een van die ontwikkelaars bent, lijkt het CFNetwork-framework misschien ontmoedigend. Er is hier echter een oplossing voor en de naam is CocoaAsyncSocket. De CocoaAsyncSocket-bibliotheek maakt interactie met contactdozen eenvoudiger en biedt ook een elegante Objective-C-interface. De huidige versie van de CocoaAsyncSocket-bibliotheek integreert netjes met Grand Central Dispatch (GCD), waardoor asynchroon programmeren een fluitje van een cent wordt.
Laten we beginnen met het bekijken van de basisprincipes van netwerken. Zonder een goed begrip van sockets, poorten en streams, zullen zelfs Bonjour en de CocoaAsyncSocket-bibliotheek je niet veel helpen!
Netwerken is niet gemakkelijk en dit is iets dat niet snel zal veranderen. Hoewel de infrastructuur die ons toegang geeft tot internet in de afgelopen decennia enorm is veranderd, zijn de onderliggende technologieën en protocollen nauwelijks veranderd. De reden is dat de services die we dagelijks gebruiken, sterk afhankelijk zijn van de onderliggende logische protocollen en veel minder van de fysieke infrastructuur. In de jaren negentig hebben de meesten van ons op internet gebladerd via een inbelverbinding. Tegenwoordig heeft de meerderheid van de mensen toegang tot een snelle breedbandverbinding en in de afgelopen jaren is een aanzienlijk deel van het internet via mobiele apparaten verbruikt. Met andere woorden, de infrastructuur is drastisch veranderd, maar de logische protocollen die nodig zijn voor routering van verkeer en interactie met applicaties zijn niet zo dramatisch veranderd.
Een andere reden dat de fundamentele technologieën en protocollen die we gebruiken om gegevens op internet te verzenden niet veel zijn veranderd, zijn omdat ze betrouwbaar, performant en robuust zijn gebleken. Die technologieën en protocollen zijn goed getest en hebben zich de afgelopen decennia ontelbare malen bewezen.
Als ontwikkelaar hebt u waarschijnlijk gehoord van sockets, poorten, adressen en dergelijke. Als u niet bekend bent met deze voorwaarden, bent u in voor een traktatie want ik zal u laten kennismaken met de wonderen van sockets, poorten, streams en protocollen. Om een basiskennis van netwerken te krijgen, is het essentieel dat u de bascis van netwerken kent, inclusief sockets en zijn vrienden.
Een netwerkverbinding werkt via sockets. Een socket is het ene uiteinde van een communicatiekanaal tussen twee processen die met elkaar willen praten. Zoals je misschien al geraden hebt, heeft een netwerkverbinding (of een kanaal voor een communicatiestroomproces) twee aansluitingen, één voor elk einde van het kanaal. Een netwerkverbinding wordt tot stand gebracht door een socket die een verbinding maakt met een andere socket, de luistercontactdoos, die luistert naar inkomende verbindingen.
Het verschil tussen een lokale en een externe socket is slechts semantisch. Vanuit het perspectief van een socket is de socket de lokale socket en is de socket waarop deze is aangesloten de externe socket. Dat is logisch. Rechts?
Terwijl een socket wordt gebruikt voor het verzenden en ontvangen van gegevens, kan een stream gegevens lezen of gegevens wegschrijven. Dit betekent dat in de meeste gevallen elke socket twee streams heeft, een voor lezen en een voor schrijven. Hoewel streams een belangrijk aspect zijn van socketprogrammering, zullen we niet direct met streams werken, omdat streams voor ons worden beheerd door de CocoaAsyncSocket-bibliotheek.
Elke socket heeft een adres dat bestaat uit de hostadres en een poortnummer. Beide delen zijn essentieel om een verbinding tot stand te brengen tussen twee sockets. Om de zaken eenvoudig te houden, is het hostadres meestal het IP-adres (Internet Protocol) van de machine terwijl het poortnummer op unieke wijze de socket op de machine identificeert. Vergelijk dit concept met een appartementencomplex. Het gebouw heeft een adres zodat mensen weten waar het te vinden is. Elk appartement in het gebouw heeft een uniek nummer zodat bezoekers van het complex het appartement kunnen vinden waarnaar ze op zoek zijn.
Het verzenden van gegevens via internet is een complex proces en heeft geresulteerd in de creatie van twee robuuste protocollen voor het uniform verzenden en ontvangen van gegevens: TCP (Transmission Control Protocol) en UDP (User Datagram Protocol). Beide protocollen zijn protocollen voor transportlaag en een deel van de internet Protocol (IP) suite.
Ik weet zeker dat TCP en UDP een belletje rinkelen bij de meesten van jullie. Er zijn verschillende belangrijke verschillen tussen beide protocollen en het is belangrijk om die verschillen te begrijpen. In deze serie zullen we ons concentreren op het TCP-protocol. Een TCP-verbinding beheert een gegevensstroom van het ene eindpunt naar het andere.
De belangrijkste verschillen tussen TCP anad UDP zijn snelheid en hoe ze omgaan netwerkbetrouwbaarheid. Als u ervoor wilt zorgen dat wat via het ene uiteinde van de verbinding wordt verzonden, aan de andere kant uitkomt, is TCP uw vriend. TCP is langzamer dan UDP, maar het heeft een goede reden om langzamer te zijn. Zonder in te gaan op te veel details, is het belangrijk om te weten dat TCP een verbinding met een handshake tot stand brengt en beëindigt om beide uiteinden van de verbinding te identificeren. Het zorgt er ook voor dat elk pakket dat via het kanaal wordt verzonden aan de andere kant aankomt. Bovendien zorgt TCP ervoor dat de volgorde van de pakketten wordt gerespecteerd.
Een van de redenen dat UDP sneller is dan TCP is omdat er geen handdruk nodig is bij het tot stand brengen en beëindigen van een verbinding. Bovendien maakt het UDP-protocol het niet uit als een pakket arriveert en het ook niet van belang is voor de volgorde waarin pakketten aankomen. Als er onderweg een pakket wordt weggelaten, probeert het UDP-protocol het niet opnieuw te verzenden omdat het niet eens weet dat het pakket wordt verwijderd. De belangrijkste zorg van UDP is dat gegevens zo snel mogelijk door het communicatiekanaal worden verzonden.
Ik ben er zeker van dat je begint te zien dat TCP en UDP heel verschillende protocollen zijn en dat elk protocol een ander doel dient. UDP is bijvoorbeeld ideaal voor het streamen van live audio en video. Snelheid is essentieel in deze situaties. Het maakt niet uit of er onderweg een pakket wordt weggelaten. Als een verwijderd pakket opnieuw zou worden verzonden, zou het te laat komen en voor livestreaming zou het niet langer relevant zijn. Online multiplayer-spellen profiteren ook van UDP. De snelheid van UDP is belangrijker dan de betrouwbaarheid. Pakketten die te laat aankomen zijn niet langer relevant en dat is het fundamentele idee achter UDP - snelheid ten opzichte van betrouwbaarheid.
TCP, aan de andere kant, heeft alles te maken met betrouwbaarheid. Het wordt gebruikt voor e-mail en surfen op internet. Het is een beetje trager, maar het zal zijn uiterste best doen om ervoor te zorgen dat u ontvangt waar u om vroeg. Het TCP-protocol is erg robuust en ondersteunt het opnieuw verzenden van verwijderde pakketten en het respecteert ook de volgorde waarin pakketten worden verzonden. Hoewel we het TCP-protocol in deze serie gebruiken, moet u er rekening mee houden dat de CocoaAsyncSocket-bibliotheek ook het UDP-protocol ondersteunt.
Op het gebied van netwerken is er nog een concept dat u moet begrijpen: het client-servermodel. In elke communicatie is er een client en een server. Vergelijk dit model met twee mensen die een telefoontje plegen. Steven wil naar Lucy bellen. Er zijn drie fundamentele vereisten om dit te laten werken.
Dit concept van een client en een server zal belangrijk worden als we Bonjour in de praktijk bekijken in het volgende artikel van deze serie. Laten we deze tutorial afsluiten met een korte blik op Bonjour.
Wat is Bonjour en hoe past het in ons verhaal? Bonjour is een technologie gemaakt door Apple en gebaseerd op Zeroconf. Het primaire doel is om het ontdekken van services eenvoudig te maken. De kans is groot dat je Bonjour vele malen hebt gebruikt zonder het te weten. Heeft u ooit een printer op uw lokale netwerk gebruikt? Is het u niet opgevallen dat het bijna geen moeite kostte om de printer te gebruiken, ook al was deze niet fysiek verbonden met uw computer? Apple's Remote iOS-applicatie maakt ook gebruik van Bonjour, en dat geldt ook voor veel andere iOS- en OS X-applicaties.
Hoewel Bonjour een geweldige technologie is, moet u er rekening mee houden dat deze niet zorgt voor het verzenden of ontvangen van gegevens. Wat Bonjour heel goed doet, is het publiceren en ontdekken van services die zich op hetzelfde lokale netwerk bevinden. In het volgende artikel zullen we Bonjour's API's van naderbij bekijken en we zullen beginnen met het bouwen van het client-servermodel dat we in dit artikel hebben besproken..
Met deze inleidende zelfstudie moet u een basiskennis hebben van netwerken, de verschillende betrokken componenten en de rol van elk onderdeel. In de resterende delen van deze serie zullen we enkele van deze componenten opnieuw bekijken en gebruiken, dus het is van cruciaal belang dat u begrijpt wat we in dit artikel hebben behandeld. In het volgende artikel zal ik meer vertellen over het client-servermodel door u te laten zien hoe u twee apparaten verbindt met Bonjour en de CocoaAsyncSocket-bibliotheek.