Hazırda mevcut olan bir react-native projem ve .Net Core projemde socket programlama ihtiyacı için hemen .Net Core tarafında ilgili SignalR kütüphanelerini indirip Hub sınıfları ve metodları bir güzel oluşturdum. Tecrübenin verdiği hızla bir güzel bitirdik, react-native tarafı içinde kolları sıvadık ama o ana kadar düşünmediğim bir şey geldi aklıma acaba react-native tarafında signalr kullanabiliyor muyum? Hemen eller titreyerek aramayı gerçekleştirdim ve react-native-signalr kütüphanesi ile karşılaştım… Hikayenin devamı makalenin detayında 🙂
ReactNative dotnetify ile .Net Core SignalR’a Bağlantı
Hazırda mevcut olan bir react-native projem ve .Net Core soket programlama ihtiyacı için hemen .Net Core tarafında ilgili SignalR kütüphanelerini indirip Hub sınıfları ve metodları bir güzel oluşturduk tecrübenin verdiği hızla bir güzel bitirdik react-native tarafı içinde kolları sıvadık ama o ana kadar düşünmediğim bir şey geldi aklıma acaba react-native tarafında signalr kullanabiliyor muyum? Hemen eller titreyerek aramayı gerçekleştirdim ve react-native-signalr kütüphanesi ile karşılaştım oh be dedim bir an.
Bu kütüphaneyi daha önce de farklı bir projede kullandığımı hatırladım 🙂 Ama asıl sürecin bundan sonra başlayacağını bilemedim çünkü daha önce kullandığım proje ile bu proje arasında bir fark vardı oda daha önce kullandığım .Net Core projesi değildi o yüzden yine titrek ellerle react-native tarafında geliştirmeleri tamamladım ve mağlesef çalışmadı korktuğum başıma gelmişti 🙁
Hemen kolları tekrar sıvayıp bu defa ne yapabiliriz için bir araştırmaya koyuldum ve .net core tarafında da büyük anlamda emek harcayıp dotnetify
adında bir kütüphane ortaya çıkardıklarını gördüm. React-native, vue, .net gibi teknoloji ve diller için kütüphaneler hazırlamışlar, açıkçası benim hoşuma gitti bu vesile ile yeni birşey öğrenmiş olduk. Dotnetify’nin çok gelişmiş kısımlarına kadar girmeyip sadece .net core tarafında random üretilen sayısal değerin react-native tarafında gerçek zamanlı olarak gösterimi ve liste elemanına gerçek zamanlı olarak nasıl yeni kayıtlar eklenir bunlar gösterilecek ayrıca hem react-native hemde .net core tarafında bu ortamın nasıl ayağa kaldırıldığını göreceğiz.
Sırasıyla .net core ve react-native tarafında hangi adımları izleyerek ortamı ayağa kaldıracağımızı göreceğiz.
.Net Core
📄 Yeni Bir .Net Core Projesi Oluşturma
.Net Core projesini isterseniz Visual Studio yada dotnet komut satırı aracını kullanarak kolaylıkla oluşturabilirsiniz tamamen tercih meselesi ama ben makale içerisinde süreçleri komut satırından yürüteceğim.
D:\Github\reactnative
dizini altına dotnetifydemo
adında bir klasör oluşturdum dotnetifydemo klasörüne react-native projesini oluşturacağım ama bu klasör altına server adında yeni bir klasör oluşturup bu klasör içerisine altta yer alan dotnet… komutu ile .net core projesini oluşturmuş olacağız.
.Net Core tarafında paket yüklemek için isterseniz Nuget Package Manager’ı kullanarak yada cli aracını kullanarak nuget paketini yükleyebilirsiniz eğer nuget paketini yüklemek için alttaki komutlardan uygun olanı kullanabilirsiniz.
Üstteki komutlardan birini kullanarak .net core promize Dotnetify.SignalR kütüphanesini yüklüyoruz ben komut satırından yükleyeceğim için .Net CLI kısmında yer alan kodu kullanarak alttaki gibi yüklüyorum.
Şimdi .Net Core tarafında dotnetify konfigürasyonunun nasıl yapılacağına ve SignalR’da Hub’a karşılık gelen BaseVM sınıflarından türeteceğimiz dotnetify Subscribe-Publisher mekanizmasının nasıl kurulacağınız makale girişinde bahsettiğimiz gibi 2 örnek ile açıklayacağız.
Paketin yüklendiğini varsayıp işlemlere devam ediyoruz Startup.cs dosyamız içerisinde ConfigureServices adlı metod içinde alttaki metodları kullanarak SignalR ve Dotnetify özelliklerini projemize kullanabilmek için kazandırıyoruz.
1 2 3 4 5 | public void ConfigureServices(IServiceCollection services) { services.AddSignalR(); // <- Eklenecek services.AddDotNetify(); // <- Eklenecek } |
Sonrasında ise yine aynı Startup.cs dosyası içerisinde Configure adlı metodda altta eklenecek diye işaretlediğimiz kısımları ekleyin.
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 | public void Configure(IApplicationBuilder app, IHostingEnvironment env) { if (env.IsDevelopment()) { app.UseDeveloperExceptionPage(); } app.UseWebSockets(); // <- Eklenecek app.UseSignalR(routes => routes.MapDotNetifyHub()); // <- Eklenecek app.UseDotNetify(); // <- Eklenecek app.Run(async (context) => { await context.Response.WriteAsync("Hello World!"); }); } |
Dotnetify ortamını geliştirme yapmak için ayağa kaldırdık. Şimdi dotnetify baseVM class’ından türeyecek SignalR’da karşılığı olan Hub sınıfımızı oluşturalım.
Eğer daha önce react-native-signalr’ı kullanarak bir react-native projesi geliştirdiyseniz dotnetify’inin işleyişi ona göre çok farklı olduğundan biraz anlama konusunda sıkıntı çıkarabiliyor mağlesef ama çokta problem olmuyor 1-2 örnek sonrası oturuyor taşlar hemen yerine.
.Net Core projemize Hubs adımda bir klasör oluşturup onun altına LiveGaugeVM adında bir sınıf oluşturuyoruz ve bu sınıf’ın Dotnetify.BaseVM sınıfından türetilmesini sağlıyoruz böylelikle Socket programlama için bir hub oluşturmuş oluyoruz. LiveGaugeVM sınıfının son hali altta yer almaktadır.
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 | using System; using System.Threading; using DotNetify; namespace dotnetify.Hubs { public class LiveGaugeVM : BaseVM { /* * Her 1sn'yede bir timer nesnesinin çalışması için 1000ms değerini burada belirliyoruz ve bu field'ı LiveGaugeVM contructor'ında yer alan timer nesnesi constructor'ında kullanıyoruz. */ private const int _timeInterval = 1000; /* * React-native tarafındaki gauge chart'ımızı beslemek için fake olarak daha üreteceğimiz timer nesnemiz. */ private Timer _timer; /* * Random olarak üretilen değerin hafızadan tutulacağı property. */ public int Value { get; set; } public LiveGaugeVM() { // Random olarak değer üreteceğimiz nesne. var random = new Random(); _timer = new Timer(state => { // 1-100 arası bir değer üretimi sağlanıyor Value adında react-native tarafında LiveGaugeVM'i kullandığımız ekranda state nesnesi içerisinde yer alan Value adındaki özelliğe buradaki değerin set edilmesi için tetiklenme sağlanıyor. Value = random.Next(1, 100); this.Changed(nameof(Value)); // PushUpdates ile yapılan değişikliklerin bu LiveGaugeVM'i kullanan aktif ilgili ekranlara yansıması sağlanıyor. PushUpdates(); }, null, _timeInterval, _timeInterval); } public override void Dispose() { _timer.Dispose(); base.Dispose(); } } } |
🌐 React Native
Alttaki komut ile istediğimiz dizine dotnetifydemo adında bir react-native projesi oluşturuyoruz.
Proje oluştuktan sonra dotnetify dizinine giderek dotnetify kütüphanesini npm üzerinden indiriyoruz.
react-native projemize dotnetify’ide yükledikten sonra alttaki gibi App.js
dosyamızda dotnetcore projemize ait url’i girelim.
Gerçek zamanlı olarak bir değeri ayrıca gauge chart’ında göstermek istediğimizden bir component’e ihtiyaç doğdu bu yüzden react-native-svg-charts adlı component’i indirdik bu component’in de react-native-svg component’ine bağımlılığı olduğundan 2 paketi alttaki komutlar ile projenize dahil ediniz.
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 | import React, { Component } from 'react'; import { StyleSheet, View, Text } from 'react-native'; import { ProgressCircle } from 'react-native-svg-charts'; import dotnetify from 'dotnetify/react-native'; // Dotnetify kütüphanesi yüklenmiş ve ayarlanmış olan .Net Core web projesinin adresini girmelisiniz! dotnetify.hubServerUrl = 'http://192.168.0.13:1453' type Props = {}; export default class App extends Component<Props> { vm constructor() { super() this.state = { Value: 50 } // BaseVM sınıfından türemiş olan ve SignalR'da hub'a karşılık gelen sınıfın adını giriyoruz. Bu sayede LiveGaugeVM sınıfındaki Value property'si ile buradaki state nesnesi içerisindeki Value değeri eşleştirmesi dotnetify kütüphanesi tarafından otomatik yapılarak değer geldikçe güncelleniyor olacak. this.vm = dotnetify.react.connect('LiveGaugeVM', this, { exceptionHandler: ex => console.log(ex) }); } componentWillUnmount() { this.vm && this.vm.$destroy(); } render() { return ( <View style={styles.container}> <Text style={styles.digital}>{this.state.Value}</Text> <ProgressCircle animate={true} style={ { height: 200, width: 200 } } progress={ this.state.Value / 100 } progressColor={'rgb(134, 65, 244)'} /> </View> ); } } const styles = StyleSheet.create({ container: { flex: 1, backgroundColor: '#fff', justifyContent: 'center', alignItems: 'center' }, digital: { fontSize: 80 } }); |
Önemli detayları üstteki kodlar arasına yazdım bu notlara dikkate alıp okumanızı öneririm özellikle dotnetify.hubServerUrl
kısmında kendi .net core projenizin adresini girmelisiniz.
Sonuç
Peki bu işi olumlu sonuçlandırdığımıza göre o zaman gerçek zamanlı olarak liste elemanı ekleme adımına geçebiliriz. Sırasıyla yine .Net Core tarafında her 1sn’yede bir listeye eleman eklenilmesini sağlayacağız.
.Net Core
.Net Core tarafında yapılması gerekenler yine ilgili açıklamaları kod blokları üzerine yazdım dikkat incelemesinizi tavsiye ederim.
Altta kod blokları arasında Faker. kod blokları göreceksiniz Fake data üretmek için sıklıkla kullandığım Faker.Net kütüphanesini yükleyebilirsiniz.
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 | using System; using System.Threading; using DotNetify; namespace dotnetify.Hubs { public class LiveListVM : BaseVM { /* * Her 1sn'yede bir timer nesnesinin çalışması için 1000ms değerini burada belirliyoruz ve bu field'ı LiveListVM contructor'ında yer alan timer nesnesi constructor'ında kullanıyoruz. */ private const int _timeInterval = 1000; /* * React-native tarafındaki People dizimizi beslemek için fake olarak data üreteceğimiz timer nesnemiz. */ private Timer _timer; public LiveListVM() { _timer = new Timer(state => { // React Native tarafında state nesnemiz içerisindeki people dizisine yeni kaydın eklenmesini sağlıyoruz. this.AddList("people", new Person { Id = Guid.NewGuid().ToString(), Name = Faker.Name.First(), Surname = Faker.Name.Last(), Age = Faker.RandomNumber.Next(18, 60) }); // PushUpdates ile yapılan değişikliklerin bu LiveGaugeVM'i kullanan aktif ilgili ekranlara yansıması sağlanıyor. PushUpdates(); }, null, _timeInterval, _timeInterval); } public override void Dispose() { _timer.Dispose(); base.Dispose(); } } } |
React Native
React native tarafında yapılan geliştirmeler ise altta kod bloğunda gözüktüğü gibi önceki gauge örneğinden tek farkı connect olduğumuz adres LiveListVM olarak değiştirilerek yeni bir connect nesnesi oluşturduk.
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 | import React, { Component } from 'react'; import { StyleSheet, View, Text, FlatList } from 'react-native'; import { ProgressCircle } from 'react-native-svg-charts'; import dotnetify from 'dotnetify/react-native'; // Dotnetify kütüphanesi yüklenmiş ve ayarlanmış olan .Net Core web projesinin adresini girmelisiniz! dotnetify.hubServerUrl = 'http://192.168.1.244:1453' type Props = {}; export default class App extends Component<Props> { vmGauge; vmList; constructor() { super() this.state = { Value: 50, people: [] } // BaseVM sınıfından türemiş olan ve SignalR'da hub'a karşılık gelen sınıfın adını giriyoruz. Bu sayede LiveGaugeVM sınıfındaki Value property'si ile buradaki state nesnesi içerisindeki Value değeri eşleştirmesi dotnetify kütüphanesi tarafından otomatik yapılarak değer geldikçe güncelleniyor olacak. this.vmGauge = dotnetify.react.connect('LiveGaugeVM', this, { exceptionHandler: ex => console.log(ex) }); // BaseVM sınıfından türemiş olan ve SignalR'da hub'a karşılık gelen sınıfın adını giriyoruz. Bu sayede LiveListVM sınıfında kullanılan AddList metodunun 2 parametresine geçilen her bir Person nesnesi için gerçek zamanlı olarak bu sınıfdaki state nesnesi içerisinde yer alan people dizisine kaydın eklenmesi dotnetify kütüphanesi tarafından otomatik yapılarak yeni bir nesne geldikçe ekleniyor olacak. this.vmList = dotnetify.react.connect('LiveListVM', this, { exceptionHandler: ex => console.log(ex) }); } componentWillUnmount() { this.vmGauge && this.vmGauge.$destroy(); this.vmList && this.vmList.$destroy(); } render() { return ( <View style={styles.container}> <FlatList style={{flex: 1}} data={this.state.people} keyExtractor={item => `${item.Id}`} renderItem={({ item }) => { return ( <View> <Text>Ad: {item.Name} {item.Surname}({item.Age})</Text> </View> ); }} /> <Text style={styles.digital}>{this.state.Value}</Text> <ProgressCircle animate={true} style={ { height: 200, width: 200 } } progress={ this.state.Value / 100 } progressColor={'rgb(134, 65, 244)'} /> </View> ); } } const styles = StyleSheet.create({ container: { flex: 1, backgroundColor: '#fff', justifyContent: 'center', alignItems: 'center' }, digital: { fontSize: 80 } }); |
Sonuç
Mutlu son…
📚 Kaynaklar
Lütfen olumlu-olumsuz tüm görüşerinizi bana yorum yada mail yolu ile iletmeyi ihmal etmeyin.
Makalede kullanılan örneğe ve React Native ile ilgili diğer tüm örneklere github hesabımdan erişebilirsiniz. Buraya tıklayıp github hesabıma erişebilirsiniz.