Skip to content

Commit

Permalink
✨ Make QR code refreshes look more random
Browse files Browse the repository at this point in the history
  • Loading branch information
guiyanakuang committed Dec 3, 2023
1 parent 8e0b527 commit 90a55aa
Show file tree
Hide file tree
Showing 3 changed files with 28 additions and 15 deletions.
Original file line number Diff line number Diff line change
@@ -1,24 +1,26 @@
package com.clipevery.model

import com.clipevery.encrypt.base64Encode
import org.signal.libsignal.protocol.IdentityKey
import java.io.ByteArrayOutputStream
import java.io.DataOutputStream

data class RequestEndpointInfo(val deviceInfo: DeviceInfo,
val port: Int,
val publicKey: IdentityKey) {
val port: Int) {

fun getBase64Encode(salt: Int): String {
val byteStream = ByteArrayOutputStream()
val dataStream = DataOutputStream(byteStream)
dataStream.writeInt(salt)
encodeDeviceInfo(dataStream)
dataStream.writeInt(port)
val serialize: ByteArray = publicKey.serialize()
dataStream.writeInt(serialize.size)
dataStream.write(serialize)
return base64Encode(byteStream.toByteArray())
val byteArray = byteStream.toByteArray()
val size = byteArray.size
val offset = salt % size
val byteArrayRotate = byteArray.rotate(offset)
val saltByteStream = ByteArrayOutputStream()
val saltDataStream = DataOutputStream(saltByteStream)
saltDataStream.write(byteArrayRotate)
saltDataStream.writeInt(salt)
return base64Encode(saltByteStream.toByteArray())
}

private fun encodeDeviceInfo(dataOutputStream: DataOutputStream) {
Expand All @@ -38,4 +40,18 @@ data class RequestEndpointInfo(val deviceInfo: DeviceInfo,
dataOutputStream.writeInt(deviceInfo.platform.bitMode)
dataOutputStream.writeUTF(deviceInfo.platform.version)
}

private fun ByteArray.rotate(offset: Int): ByteArray {
val effectiveOffset = offset % size
if (effectiveOffset == 0 || this.isEmpty()) {
return this.copyOf() // 如果偏移量为0或数组为空,则直接返回原数组的副本
}

val result = ByteArray(this.size)
for (i in this.indices) {
val newPosition = (i + effectiveOffset + this.size) % this.size
result[newPosition] = this[i]
}
return result
}
}
2 changes: 1 addition & 1 deletion composeApp/src/desktopMain/kotlin/com/clipevery/main.kt
Original file line number Diff line number Diff line change
Expand Up @@ -73,7 +73,7 @@ fun initKoinApplication(ioScope: CoroutineScope): KoinApplication {
single<ClipServer> { DesktopClipServer().start() }
single<ClipClient> { DesktopClipClient() }
single<DeviceInfoFactory> { DesktopDeviceInfoFactory() }
single<QRCodeGenerator> { DesktopQRCodeGenerator(get(), get(), get()) }
single<QRCodeGenerator> { DesktopQRCodeGenerator(get(), get()) }
single<GlobalCopywriter> { GlobalCopywriterImpl(get()) }
single<ClipboardService> { getDesktopClipboardService(get()) }
single<TransferableConsumer> { DesktopTransferableConsumer() }
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -7,22 +7,19 @@ import com.clipevery.model.RequestEndpointInfo
import com.clipevery.net.ClipServer
import com.google.zxing.BarcodeFormat
import com.google.zxing.qrcode.QRCodeWriter
import org.signal.libsignal.protocol.state.IdentityKeyStore
import java.awt.Color
import java.awt.image.BufferedImage

class DesktopQRCodeGenerator(private val clipServer: ClipServer,
private val deviceInfoFactory: DeviceInfoFactory,
private val identityKeyStore: IdentityKeyStore): QRCodeGenerator {
private val deviceInfoFactory: DeviceInfoFactory): QRCodeGenerator {

private var salt: Int = 0

private fun bindInfo(): String {
salt = (0..Int.MAX_VALUE).random()
salt = (0..999999).random()
val deviceInfo = deviceInfoFactory.createDeviceInfo()
val port = clipServer.port()
val publicKey = identityKeyStore.identityKeyPair.publicKey
return RequestEndpointInfo(deviceInfo, port, publicKey).getBase64Encode(salt)
return RequestEndpointInfo(deviceInfo, port).getBase64Encode(salt)
}

override fun generateQRCode(width: Int, height: Int): ImageBitmap {
Expand Down

0 comments on commit 90a55aa

Please sign in to comment.