Bu blog yazısı, diğer blog kitabım olan Cybersecurity for Executives in the Age of Cloud gibi geleceğin kitabı olabilecek güvenli kodlama ilkelerine ilişkin bir dizinin parçasıdır . Kitabın ne zaman yayınlanacağını bilmek istiyorsanız, beni Medium'da veya Twitter'da veya her ikisinde de takip edin!
Son yazımda, arka ofis bankacılığı ve vergi sistemleri üzerinde çalışırken röportajlarda sıkça sorduğum bir soru yönelttim:
Let’s say you have a system that makes calls across a network to update the money in a bank account. The network connection times out before you get a response from the system to which you made the request. How do you handle that? Possible answers: * Resend the transaction to make sure it went through. * Assume it went through and don’t do anything because you don’t want the person to get a double payment. Or something else?
Muhasebe Sistemlerinde İşlemler
Banka hesapları arasında para transferi yapmak veya bir ATM'den para çekmek için de bir işlem yapılabilir. Bu durumda, muhasebe açısından, bir banka hesabının borçlandırılması ve birinin alacaklandırılması gerekir. Bir borç, bir varlık hesabını artıracak veya bir borç hesabını artıracaktır. Bir kredi tam tersini yapacaktır. Bir işlemi kaydetmek için bir muhasebe sistemini güncellediğinizde, genellikle iki işlem yapmanız gerekir: borç ve alacak. Her iki işlemi de yapmazsanız, hesaplarınız bakiyesiz olacaktır.
Güvenlik söz konusu olduğunda, bir işlemin bir kısmının başarısız olmasına neden olacak bir yol bulabilen bir saldırgan, sistemin gerektiği zaman hesaplarından para çekmemesine ve saldırganın sahip olduğu değeri aşan birden çok işlem yapmasına izin verebilir. onların hesabı. Bu nedenle ve iyi mali kayıtlar tutmak için, gerekli işlemlerin her zaman gerçekleştiğinden veya hiç gerçekleşmediğinden emin olmanız gerekir.
Bu blog yazısının başında yayınladığım örneği düşünün. Bir hesaba para ekleyen ve diğerinden düşen bir finansal işlem gerçekleşir. Saldırgan, ilk operasyonun başarılı olmasına ve ikincisinin başarısız olmasına neden olacak bir yol bulur. Saldırganın iki hesabı var. Hesaplardan birine diğerinden kesinti yapmadan para ekleme işlemini tekrar tekrar yaparlar. Şimdi, her iki hesabın değerini de eklediğinizde, saldırganın eskisinden daha fazla parası var.
“Gün Sonu”, tüm muhasebe kayıtlarının doğru olmasını sağlamak için gün sonunda yapılması gereken tüm mutabakatlar ve işlemler yapılırken kullanılan bir terimdir. Üniversitede Mt. Rainier Ulusal Parkı'nda snack bar müdürü olarak çalışırken, günün sonunda tüm parayı toplamam ve yazar kasa kayıtlarıyla karşılaştırmam ve Paradise Lodge'daki ofise yatırmam gerekiyordu. Bankacılık sistemleri benzer bir şey yapar.
Saldırgan senaryomuzdaki gibi hataları bulmak için muhasebe süreçleri mutabakat denilen bir şey içerir. Bu işlem sırasında, hesaplar veya muhasebeciler, defterlerin dengesini sağlamak için hesaplamalar yapacaktır. Arka ofis bankacılık sistemlerinde, genellikle gün sonu işlemleri sırasında sistemin ürettiği raporları gözden geçirirler. Örneğimiz için mutabakat işlemini gerçekleştirirken borç ve alacakların bir araya gelmediğini görmeleri ve hatayı bulmaları gerekir. Ancak, saldırgan parasını zaten çekmişse, çok geç olacaktır, bu nedenle hatayı en baştan önlemek daha iyidir.
İşlemleri içeren muhasebe ve finansal sistemlerin manipüle edilebileceği pek çok yol vardır. Temettüleri hesaplayıp dağıttıktan sonra hesap bakiyelerinin iki şirket arasında transfer edilmesi gereken karmaşık bir temettü işleme sistemi üzerinde çalıştım. Bu aktarımın nasıl gerçekleştiği, aktarımın hesaplanma ve işlenme biçiminde hataya yer bıraktı. Bunu, gerçekleştiğinde işlemin manipülasyonuna izin vermeyecek bir kod oluşturarak düzelttim.
Temettü hesaplamalarının her biri, sayıları işlemek için farklı kodlara ve yöntemlere sahipti. İşlemler bir seferde toplu olarak işlendi. Toplanması gereken her şey ve bu temettü işleme sistemini aldığımda, günün sonunda rastgele tutarsızlıklar vardı. Bunu da düzelttim.
Ayrıca bir keresinde vergileri her ay yanlış hesaplayan bir vergi sistemi üzerinde çalışmıştım - 300.000 $'a varan oranlarda! Bunu da sağlam işlem mantığı ve diğer bölümlerde açıklayacağım başka mekanizmalar kullanarak düzelttik. Kod yayınlandığında 23 dolardan kurtulmuştuk ve ben üzülmüştüm. Bu nasıl olabildi? Şirketteki finans uzmanları bunun önemsiz olduğunu söyledi, ancak böyle bir şeyin koduma girmesine izin vermediğimden emindim. Ekibimin başka bir üyesinin yuvarlama hatasıyla bazı kodlar eklediği ortaya çıktı. Düzelttik.
Önceki kitabımda başka bir finansal işlem türü hakkında yazmıştım. Bir müşteri hesap açtığında diğer bankalardan para transfer etme sürecini iyileştirmek için çalışıyordum. Gereksiz bir kod satırı, daha sonra çözdüğüm sistemde bazı garip para transferlerine yol açtı. Bunların hepsini burada tekrar etmeyeceğim, ancak finansal işlemlerin zor olduğunu anlayın! Her kod satırı incelenmelidir.
Yazılım programlamasında işlem, belirli bir kod bloğunu çalıştırmaya başlamanıza ve ardından bir hata oluştuğunda kodun yaptığı tüm eylemleri geri almanıza izin veren bir yapıdır.
İşlemler genellikle veritabanı kodunda kullanılır. Birçok finansal sistem, bir finansal işlem gerçekleştiğinde veritabanında parayı hareket ettirmek için veritabanı kodu yazmak için SQL (Yapılandırılmış Sorgu Dili) kullanır. Onları çalıştığım bankada arka ofis programlamasında çok kullandık. Bu tür işlemler genellikle ilişkisel veritabanı sistemleri tarafından desteklenir . Bir sonraki bölümde farklı NoSQL veritabanı sistemleri hakkında daha fazla bilgi.
Çoğu zaman bir veritabanında finansal işlem yaptığınızda birden fazla kod satırı gerekir. İlk olarak, parayı bir hesaptan çıkarmanız gerekir. Ardından, başka bir hesaba eklemek için bir kod satırı yazmanız gerekir. Veritabanındaki bir hesaptan 100 çıkarmak ve onu diğerine eklemek için kodun genel olarak nasıl göründüğünü size göstermek için bazı sözde SQL'ler:
//subtract money from the sending bank account update bank_account set balance = balance - 100 where account_number = 1234 //add money to the receiving bank account update bank_account set balance = balance + 100 where account_number = 5678
Bu senaryo gerçekleşirse, hesaplarınız doğru değildir. Veritabanının yalnızca ikinci hesabı da güncelleyebiliyorsa ilk hesabı güncellemesini istersiniz. İşlemlerin devreye girdiği yer burasıdır. Kodu, bir hata işleyiciyi nasıl kullandığınıza benzer şekilde, bir işleme sararsınız. Aradaki fark, bir hata oluştuğunda, veritabanına hata oluşmadan önce yürüttüğü satırlardan herhangi birini geri almasını söyleyebilirsiniz.
İşte bu kodun nasıl görünebileceğine dair bir örnek.
BEGIN TRY BEGIN TRANSACTION //subtract money from the sending bank account update bank_account set balance = balance - 100 where account_number = 1234 //add money to the receiving bank account update bank_account set balance = balance + 100 where account_number = 5678 COMMIT END TRY BEGIN CATCH IF @@TRANCOUNT > 0 ROLLBACK END CATCH
Bu çok basit bir işlem örneğidir. Diyelim ki, bir tarafında birden fazla değer içeren ve diğer tarafında bir değer içeren ve hiçbir işlem içermeyen bir işleminiz var. Bu kodun bir Java uygulamasında satır içi SQL ifadeleriyle yürütüldüğünü varsayalım (yani saklı yordam yok). Java uygulaması, değerleri üçüncü bir taraftan alınan düz bir dosyadan alır. Genellikle bir CSV dosyası olur.
function (transfer_amount, fee, customer_account_1, customer_account_2, bank_fee_account) //add money to the receiving bank account update bank_account set balance = balance + transfer_amount where account_number = customer_account1 //Subtract money sending bank account update bank_account set balance = balance - transfer_amount where account_number = customer_account2 //subtract wire transfer fee from sending bank account update bank_account set balance = balance - fee where account_number = customer_account2 //Add money sending bank account update bank_account set balance = balance + fee where account_number = bank_fee_account
Bu senaryoda, alacaklar ve borçlar dengededir. Mutabakat süreci, özellikle ücret bakiyesinin sistem tarafından işlenen banka havalesi sayısıyla uyumlu olup olmadığını görmek istemiyorsa, mutabakatı gerçekleştirenlere bir sorun olduğunu gösteren hiçbir kırmızı bayrak gösterilmez. Ancak müşteri ücret ödemeden banka havalesi göndermek zorunda kaldı.
Bir işlem bunu düzeltirdi. Ücreti düşerken bir hatayla karşılaşırsa hesap transferini geri alır:
BEGIN TRY BEGIN TRANSACTION //add money to the receiving bank account update bank_account set balance = balance + transfer_amount where account_number = customer_account1 //Subtract money sending bank account update bank_account set balance = balance - transfer_amount where account_number = customer_account2 //subtract wire transfer fee from sending bank account update bank_account set balance = balance - fee where account_number = customer_account2 //Add money sending bank account update bank_account set balance = balance + fee where account_number = bank_fee_account COMMIT END TRY BEGIN CATCH IF @@TRANCOUNT > 0 ROLLBACK END CATCH
Artık işlemleri kullanmak için can atıyorsunuz, değil mi? İşlemlerin tabloları kilitleyebileceğine dikkat edin, böylece işlem işlenirken başka hiçbir yazma işlemi gerçekleşemez. Bu, performans sorunlarına yol açabilir. Bir e-ticaret sitesindeki bir tablo, veritabanını kilitlerse, insanlar sipariş vermeyebilir. Benim üzerinde çalıştığım gibi bir yatırım sitesinde insanlar ticaret yapamayabilir.
Bir veritabanı kilidi güvenliğinize yardımcı olabilir. Finansal hesaplamalar yaparken diğer işlemlerin onlara dokunmasını önlemek için tabloları kilitleyebilirsiniz. Örneğin, gün sonu işleme ve hesap mutabakatı sırasında kilitler, bu işlem tamamlanana kadar herhangi bir şeyin değişmesini önleyecektir. Belki kitapta veritabanı kilitleri hakkında daha fazla yazacağım, ancak tabloları kilitlerken performans sorunlarının dikkate alındığını unutmayın.
https://docs.microsoft.com/en-us/dynamics365/business-central/admin-view-database-locks
Sonunda Tutarlı
NoSQL veritabanları ilk ortaya çıktığında çoğu işlemleri desteklemiyordu. NoSQL veritabanları, verileri yapısal olarak farklı bir şekilde depolayarak daha iyi performans ve güvenilirliği hedefler. Ayrıca, çoğu sonunda tutarlıydı . Bunun anlamı, bir işlem gerçekleştiğinde, ilgili verileri depolayan tüm veritabanlarında hemen görünmeyecek olmasıdır.
Örneğin, onu destekleyen üç veritabanı sunucusuna sahip bir sisteminiz olabilir. Üç veritabanı sunucusu, biri çökerse uygulamanın çalışmaya devam etmesini sağlamak için birbirinin kopyaları olabilir. Gecikmeyi azaltmak için veri tabanınızı işlemenin gerçekleştiği yerin yakınına da yerleştirmek isteyebilirsiniz.
Bazen üç farklı bölgedeki veritabanlarını besleyen günlükleriniz olur, ancak sonunda hepsinin tek bir veritabanında sonuçlanması gerekir. AWS'nin Frankfurt, Almanya bölgesinde bir günlüğünüz görünebilir. ABD ve Kanada'da iki veritabanı daha var. Birisi ABD günlük sunucusunu sorgular ve bu günlük kaydını hemen görmez, ancak sonunda veritabanları senkronize edildiğinde göreceklerdir.
Bu, bir kayıt sistemi için uygun olabilir, ancak bir finansal sistem düşünün. ABD'deki hesabınızda 1000$ olan bir hesabınız var. Almanya'da biri ATM'den 1000 dolar çekiyor. Aynı zamanda, biri ABD'de bir ATM'den 1000 dolar çekiyor. ABD veri tabanı henüz Almanya'daki ATM işleminin tüm parayı çektiğini gösteren güncellemeyi almadığı için her iki işlem de gerçekleşiyor.
Bu nedenle işlemler yapılırken tablolar kilitlenir. Bir sonraki işlemin başlayabilmesi için bir işlemin tamamlanması gerekir. Dağıtılmış veritabanlarının zorlu olmasının nedeni de budur! Dünya genelinde olası ağ sorunları ve gecikmesi olan tabloları kilitlemek sorunlara neden olabilir.
Bu arada, Bitcoin'in nihayetinde tutarlı olup olmadığını ve bu para biriminde işlem yapmayı seçerseniz bunun sizi nasıl etkileyebileceğini anlamak isteyebilirsiniz . Burada o tartışmaya girmeyeceğim. Konuyla ilgili birçok makale ve araştırma makalesi bulabilirsiniz. Diğer kripto para birimlerinin de benzer düşünceleri olabilir.
Bazı NoSQL veritabanları artık işlemleri desteklemektedir. Onları test etmedim ama teoride, ilişkisel veritabanlarının sunduğu benzer işlem işlevselliğini sağlayabilmeleri gerekir.
Uygulama Kodundaki İşlemler
Mümkün olduğunca veritabanlarında finansal hesaplamalar yapmayı tercih ederim. Güvenlik nedenleriyle neden saklı yordamları da kullanmanız gerektiğini gelecekteki bir gönderide açıklayacağım. Uyumsuz işleme veya veri türleri riskini en aza indirmek için işlemlerin tek bir tür platformda tek bir kod türüyle yazılmasını tercih ederim, ayrı bir bölümün konusu. Ek olarak, ilişkisel veritabanları, oradaki en zeki kişilerden bazıları tarafından veri bütünlüğü göz önünde bulundurularak yazılır. Veritabanları inanılmaz derecede performanslıdır ve karmaşıktır! Verileri verimli bir şekilde depolamak ve işlemek içindir. Bu onların tek amacıdır.
Ancak bazen uygulama kodunuzda bir işlem yapmak daha mantıklıdır. Veritabanındaki tek bir saklı yordam tarafından ele alınamayacak şekilde bir işlemin iki adımının gerçekleşmesini gerektiren belirli bir web tasarımımız vardı.
DBA, tüm uygulamayı yeniden tasarlamamızı istedi. Bunun yerine uygulama katmanında bir işlem kullanabileceğimizi savundum. Bu bir yargı çağrısıdır. Uygulama katmanında çalışan birinin neden var olduğunu anlamadığı için işlem kodunu daha sonra kaldırmamasını sağlayacak sağlam süreçleriniz var mı?
Her halükarda, kodu doğru bir şekilde oluşturmak için uygulama katmanında çalışan kişiye güvendim. Sistemi üretime teslim ettiğimizde hatasız bir şekilde harika çalıştı. Geliştirilmiş kullanıcı arayüzü, şirkete yeni gelen transferlerde çok para kazandırdı (transfer departmanındaki birinin dediği gibi fax-a-souras-rex'e kıyasla).
Uygulama katmanı kodunuzdaki bir işlem, veritabanı kodunuzla hemen hemen aynı şekilde çalışır. İşte C# ile yazılmış bir işlem örneği:
using (IDbTransaction tran = conn.BeginTransaction()) { try { // your code tran.Commit(); } catch { tran.Rollback(); throw; } }
izolasyon seviyeleri
Herhangi bir dilde bir işlem kullanacaksanız, başlamadan önce belgelerin ayrıntılarını inceleyin ve nasıl çalıştıklarını tam olarak anladığınızdan emin olun. İşleminizin farklı senaryolarda nasıl davranacağını etkileyen farklı özellikleri anladığınızdan emin olun. Örneğin, .NET, bir işlem uçuş halindeyken verilerin okunup okunamayacağını gösteren farklı yalıtım seviyelerine sahiptir.
Veritabanlarının benzer kavramları vardır.
Kısmen güncellenmiş bilgilerin alınmasını önlemek için, bir işlem devam ederken kişilerin verileri okumasını engellemek isteyebilirsiniz. Banka hesabı örneğimizde, bir hesap borçlandırılabilir, ancak diğeri henüz kredilendirilmemiş olabilir ve bu verileri görüntüleyen biri bir hata oluştuğunu düşünebilir. Diğer durumlarda, örneğin bir video oyunundaki puanları görüntülemek gibi, bir işlem işlenirken verilerin biraz kapalı olması önemli değildir. Bu tasarım sorunları çok zorlaşabilir ve bir kez daha, olası sorunları ve ödünleşimleri düşünmek ve doğru yapmak için biraz yazılım mühendisliği gerektirir.
İşlemler ve ağlar
Yazımın başında bir soru sormuştum. Başka bir banka hesabına para eklemek için İnternet üzerinden bir işlem gönderiyorsunuz ve talebiniz zaman aşımına uğradı. Yanıtı hiç alamadınız, ancak diğer sistemin verileri alıp işlemesi ihtimali var. Ya da belki yapmadılar.
Diyelim ki SQL saklı yordamınızda bir işlem kullanıyorsunuz ve sistem zaman aşımı nedeniyle işlem geri alındı. Parayı gönderen banka hesabı için yerel kayıtlarınızda herhangi bir parayı azaltmadınız. Peki ya diğer sistem isteği alır ve zaman aşımına neden olan bir sorundan önce işleme koyarsa?
Sorumun doğru cevabı, diğer sistemdeki kayıtları sorgulamadan işlemin başarılı olup olmadığını bilemezsiniz. İşlem hatasını, ağ zaman aşımına uğradığınızı gösteren bir tür kodla işaretlemelisiniz. Ardından, sistemi yeniden işlemeniz gerekip gerekmediğini belirlemek için diğer sistemi sorgulayın.
İşlemleri yönetmek çok zor olabilir ve beklenmeyen bir hatanın dengesiz hesaplara veya daha da kötüsü fon kaybına yol açmadığından emin olmak için mantıklı düşünmeyi gerektirir.
Bitcoin'i ilk araştırdığımda konuyla ilgili bir kitaba göz gezdirdim. Kripto para birimlerinin riskli olmasının birçok nedeni görüyorum, ancak özellikle gözüme çarpanlardan biri “çifte harcama” oldu. Elbette, kripto para birimine inanmanızı ve Bitcoin'e yatırım yapmanızı isteyen herkes, teknik olarak mümkün olsa da, riskin çok düşük olduğunu ve bunun asla gerçekleşmediğini söyleyecektir. Merak etme.
Rakamların toplandığı veya toplanmadığı bankacılık sistemleri üzerinde çalıştıktan sonra, yalnızca bu olasılığa dayanarak Bitcoin'in benim için olmadığına karar verdim. Bu olasılığın çok nadir ve pek olası olmadığını düşünseniz bile, bu, insanların hafife aldığı Kara Kuğu olaylarından biri olabilir. Bir Siyah Kuğu olayı, çok fazla hasara neden olabilecek son derece olasılık dışı bir olaydır. Bunu ve risk kararlarıyla ilgili diğer hatalı mantığı bu kitapta ve daha da çok sevdiğim ikinci kitapta okuyabilirsiniz.
Bunun bir sorun olduğunu düşünmüyorsanız, kendinize gelin. Ben katılmamayı seçiyorum. Bir noktada banka kullanmanın riski, olası çifte harcamanın yarattığı riski ve parasal kayba neden olabilecek diğer riskleri aşarsa, fikrimi değiştirme hakkımı saklı tutarım. Ancak bankacılık sistemleri üzerinde çalıştıktan sonra bu noktada onlara daha çok güveniyorum. Ücretler, benim gibi bu sistemleri güvende tutan ve işlemin istenen sonuca sahip olmasını sağlayan kişilerin maaşlarını desteklemek için var.
© 2. Sight Laboratuvarı 2021
Bu blog yazısında listelenen bu serideki daha fazlası:Tasarıma Göre Güvenli Kod
____________________________________________
Siber Güvenlik ve Bulut Güvenliği hakkında daha fazla bilgi edinmek ister misiniz? Kontrol edin: Amazon'da Bulut Çağında Yöneticiler için Siber Güvenlik
Bulut Güvenliği Eğitimine mi ihtiyacınız var? 2. Sight Lab Bulut Güvenliği Eğitimi
Bulutunuz güvenli mi? Sızma testi veya güvenlik değerlendirmesi için 2. Gözetleme Laboratuvarı'nı işe alın .
Siber Güvenlik veya Bulut Güvenliği Sorunuz mu var? IANS Research ile bir görüşme planlayarak Teri Radichel'e sorun .
Teri Radichel'den Siber Güvenlik ve Bulut Güvenliği Kaynakları: Siber Güvenlik ve Bulut güvenliği sınıfları, makaleler, teknik incelemeler, sunumlar ve podcast'ler
Yaz sonu ve sonbahar nostaljik mevsimlerdir. Sokak lambaları ışıklarını yağmurlu sokaklara saçıyor ve ayakların altındaki yapraklar - alacakaranlığın gölgelerinde soluk kırmızı-turuncu - geçmiş günlerin bir hatırlatıcısı.
Angular uygulamanızın bazı bölümlerinin neden hala yavaş olduğunu merak ediyor musunuz? Bu makale, uygulama performansınızı nasıl artırabileceğinizi size gösterecek. Angular uygulamalarınızı gecikmeli ve yavaş buluyor ancak bunları nasıl geliştireceğiniz konusunda hiçbir fikriniz yok mu? Uygulamanızın performansını artırmanın yaklaşık 5 yolunu öğrenmek için doğrudan bu makaleye dalalım.
"Tren kazası" kelimesinden nefret ediyorum. İnsanlar kendi ahlaki pusulalarında teselli bulur ve bunu yaparken kendilerini yargıda bulunurken bulurlar.
Bugün farklı bir yolculuğa çıkıyoruz. Çoğunlukla resimler.
Bu ay tüm yeni abonelerimize ve yazarlarımıza sıcak bir karşılama; sürülerinizde ortaya çıkıyorsunuz ve bunun için size teşekkür ediyoruz. Burada harika bir topluluk oluşturuyoruz ve yorumlarınızı ve makalelerinizi okumak harika.
İster NFT'lerde yeni olun, ister sahnenin emektarı olun, burada anlattıklarımın faydalı olabileceğini umuyorum. Bu seri, "projelerin" herkesi kendilerine bir miktar para kazandırmak için manipüle etmek için kullandıkları özenle tasarlanmış yöntemleri ortaya çıkarmayı amaçlıyor.