diff --git a/.swiftpm/xcode/xcshareddata/xcschemes/Blockchain.xcscheme b/.swiftpm/xcode/xcshareddata/xcschemes/Blockchain.xcscheme
new file mode 100644
index 0000000..31501f9
--- /dev/null
+++ b/.swiftpm/xcode/xcshareddata/xcschemes/Blockchain.xcscheme
@@ -0,0 +1,102 @@
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
diff --git a/.swiftpm/xcode/xcuserdata/vbodinaud.xcuserdatad/xcschemes/xcschememanagement.plist b/.swiftpm/xcode/xcuserdata/vbodinaud.xcuserdatad/xcschemes/xcschememanagement.plist
index 5026709..670d047 100644
--- a/.swiftpm/xcode/xcuserdata/vbodinaud.xcuserdatad/xcschemes/xcschememanagement.plist
+++ b/.swiftpm/xcode/xcuserdata/vbodinaud.xcuserdatad/xcschemes/xcschememanagement.plist
@@ -9,6 +9,27 @@
orderHint
0
+ CryptoSwift (Playground) 1.xcscheme
+
+ isShown
+
+ orderHint
+ 2
+
+ CryptoSwift (Playground) 2.xcscheme
+
+ isShown
+
+ orderHint
+ 3
+
+ CryptoSwift (Playground).xcscheme
+
+ isShown
+
+ orderHint
+ 1
+
SuppressBuildableAutocreation
diff --git a/Package.resolved b/Package.resolved
index 1dbca2c..ada42b9 100644
--- a/Package.resolved
+++ b/Package.resolved
@@ -6,8 +6,8 @@
"repositoryURL": "https://github.com/krzyzanowskim/CryptoSwift.git",
"state": {
"branch": null,
- "revision": "a44caef0550c346e0ab9172f7c9a3852c1833599",
- "version": "1.3.0"
+ "revision": "5669f222e46c8134fb1f399c745fa6882b43532e",
+ "version": "1.3.8"
}
}
]
diff --git a/Package.swift b/Package.swift
index 8ab9fcc..73f6be6 100644
--- a/Package.swift
+++ b/Package.swift
@@ -5,6 +5,9 @@ import PackageDescription
let package = Package(
name: "Blockchain",
+ platforms: [
+ .macOS(.v10_12),
+ ],
dependencies: [
// Dependencies declare other packages that this package depends on.
// .package(url: /* package url */, from: "1.0.0"),
diff --git a/Sources/Blockchain/Models/Block.swift b/Sources/Blockchain/Models/Block.swift
index 50c0e72..5673a5c 100644
--- a/Sources/Blockchain/Models/Block.swift
+++ b/Sources/Blockchain/Models/Block.swift
@@ -17,6 +17,19 @@ class Block {
var nonce: Int
var timestamp: Int
+ /**
+ Initialize a block with the provided parts and specifications.
+
+ - parameters:
+ - hash: The hash of the block
+ - data: The data of the block
+ - previousHash: The hash of the previous block
+ - index: The index of the block
+ - nonce: The nonce of the block
+ - timestamp: The timestamp of the block
+
+ - returns: A beautiful new block for the blockchain.
+ */
init(hash: String = "", data: String = "", previousHash: String = "", index: Int = 0, nonce: Int = 0, timestamp: Int = 0) {
self.data = data
self.previousHash = previousHash
@@ -26,10 +39,20 @@ class Block {
self.hash = hash
}
+ /**
+ Generate the hash of the block.
+
+ - returns: The hash of the block
+ */
func generateHash() -> String {
return data.sha256()
}
+ /**
+ Generate the timestamp of the block
+
+ - returns: The timestamp of the block
+ */
func generateTimestamp() -> Int {
return Int(Date().timeIntervalSince1970)
}
diff --git a/Sources/Blockchain/Models/Blockchain.swift b/Sources/Blockchain/Models/Blockchain.swift
index c19854e..f82add9 100644
--- a/Sources/Blockchain/Models/Blockchain.swift
+++ b/Sources/Blockchain/Models/Blockchain.swift
@@ -11,6 +11,12 @@ import Foundation
class Blockchain {
var chain = [Block]()
+ /**
+ Initialize the first block of the blockchain.
+
+ - Parameters:
+ - data: The datas of the block
+ */
func createGenesisBlock(data: String) {
let genesisBlock = Block()
genesisBlock.data = data
@@ -20,19 +26,63 @@ class Blockchain {
genesisBlock.timestamp = genesisBlock.generateTimestamp()
genesisBlock.hash = genesisBlock.generateHash()
chain.append(genesisBlock)
- print("Genesis block created -- hash: \(genesisBlock.hash ?? "")")
+ print("Genesis block created -- hash: \(genesisBlock.hash)")
}
+ /**
+ Initialize a new block of the blockchain.
+
+ - Parameters:
+ - data: The datas of the block
+ */
func createBlock(data: String) {
let newBlock = Block()
newBlock.data = data
- newBlock.previousHash = chain[chain.count-1].hash
+ newBlock.previousHash = chain.last!.hash
newBlock.index = chain.count
newBlock.nonce = 0
newBlock.timestamp = newBlock.generateTimestamp()
newBlock.hash = newBlock.generateHash()
chain.append(newBlock)
- print("Block \(newBlock.index ?? 0) created -- hash: \(newBlock.hash ?? "") previous hash: \(newBlock.previousHash ?? "") data: \(newBlock.data ?? "")")
+ print("-- Block \(newBlock.index) created --\n hash: \(newBlock.hash)\n previous hash: \(newBlock.previousHash)\n data: \(newBlock.data)")
+ }
+
+ /**
+ Insert a corrupted block in the blockhain.
+ (for testing purpose)
+ */
+ func insertCorruptedBlock() {
+ let newCorruptedBlock = Block()
+ newCorruptedBlock.data = "Corrupted block"
+ newCorruptedBlock.previousHash = "1234567890"
+ newCorruptedBlock.index = chain.count
+ newCorruptedBlock.nonce = 0
+ newCorruptedBlock.timestamp = newCorruptedBlock.generateTimestamp()
+ newCorruptedBlock.hash = newCorruptedBlock.generateHash()
+ chain.append(newCorruptedBlock)
+
+ print("-- Corrupted block \(newCorruptedBlock.index) created --\n hash: \(newCorruptedBlock.hash)\n previous hash: \(newCorruptedBlock.previousHash)\n data: \(newCorruptedBlock.data)")
+ }
+
+ /**
+ Check validity of the blockchain.
+ */
+ func chainValidity() {
+ var isChainValid = true
+ var corruptedBlock = Block()
+
+ for i in 1...chain.count-1 {
+ if chain[i].previousHash != chain[i-1].hash {
+ isChainValid = false
+ corruptedBlock = chain[i]
+ }
+ }
+
+ print("Chain is valid : \(isChainValid)")
+
+ if !isChainValid {
+ print("Corrupted block is : \(corruptedBlock.index)")
+ }
}
}
diff --git a/Sources/Blockchain/main.swift b/Sources/Blockchain/main.swift
index 07965d5..8b369a1 100644
--- a/Sources/Blockchain/main.swift
+++ b/Sources/Blockchain/main.swift
@@ -17,16 +17,28 @@ repeat {
print("Enter command:")
command = readLine()
+ // Create a new block
if command == "create" {
print("data for the new block:")
let data = readLine()
blockchain.createBlock(data: data ?? "")
}
+ // Create a lot of blocks
if command == "spam" {
for _ in 1...1000 {
blockchain.createBlock(data: "\((blockchain.chain.last?.index ?? 0)+1)")
}
}
+ // Check validity of the blockchain
+ if command == "validity" {
+ blockchain.chainValidity()
+ }
+
+ // Insert a corrupted block
+ if command == "corrupt" {
+ blockchain.insertCorruptedBlock()
+ }
+
} while command != "exit"