Skip to content
This repository has been archived by the owner on Jun 27, 2023. It is now read-only.

hex strings #18

Closed
tanner0101 opened this issue Aug 24, 2016 · 5 comments
Closed

hex strings #18

tanner0101 opened this issue Aug 24, 2016 · 5 comments
Milestone

Comments

@tanner0101
Copy link
Member

Add the ability to init Bytes from a hex string and also to convert bytes to hex strings.

public protocol SequenceInitializable: Sequence {
    init(_ sequence: [Iterator.Element])
}

/**
    Provides access to hexStrings

    Move to vapor/core
*/
extension SequenceInitializable where Iterator.Element == Byte {

    public init(hexString: String) {
        var data = Bytes()

        var gen = hexString.characters.makeIterator()
        while let c1 = gen.next(), let c2 = gen.next() {
            let s = String([c1, c2])

            guard let d = Byte(s, radix: 16) else {
                break
            }

            data.append(d)
        }

        self.init(data)
    }
}

extension Sequence where Iterator.Element == Byte {
    public var hexString: String {
        #if os(Linux)
            return self.lazy.reduce("") { $0 + (NSString(format:"%02x", $1).description) }
        #else
            let s = self.lazy.reduce("") { $0 + String(format:"%02x", $1) }

            return s
        #endif
    }
}
@tanner0101 tanner0101 added this to the 0.4.3 milestone Aug 24, 2016
@tanner0101
Copy link
Member Author

tanner0101 commented Sep 11, 2016

Also base64 decode

extension CipherProtocol {
    public func decrypt(_ bytes: Bytes, key: Bytes? = nil) throws -> Bytes {
        return try decrypt(bytes, key: key ?? defaultKey, iv: defaultIV)
    }

    public func decrypt(_ string: String, key: Bytes? = nil, encoding: CipherEncoding = .base64) throws -> String {
        let bytes: Bytes

        switch encoding {
        case .hex:
            var data = Bytes()

            var gen = string.characters.makeIterator()
            while let c1 = gen.next(), let c2 = gen.next() {
                let s = String([c1, c2])

                guard let d = Byte(s, radix: 16) else {
                    break
                }

                data.append(d)
            }
            bytes = data
        case .base64:
            bytes = string.base64Decoded
        }

        let d = try decrypt(bytes, key: key)
        return d.string
    }
}

extension String {
    public var base64Decoded: Bytes {
        guard let data = NSData(base64Encoded: self, options: []) else { return [] }
        var bytes = Bytes(repeating: 0, count: data.length)
        data.getBytes(&bytes,  length: data.length)
        return bytes
    }
}```

@loganwright
Copy link
Member

loganwright commented Feb 8, 2017

We can't do this until Swift 4 because we can't add initializers to generic array extensions, let's revisit this at that point.

@tanner0101
Copy link
Member Author

It should be able to work exactly the same way that base64Encoded works.

bytes.hexEncoded.string
string.bytes.hexDecoded

@tanner0101 tanner0101 reopened this Feb 15, 2017
@loganwright
Copy link
Member

Yup, we can add properties, just can't do the traditional convertible pattern we've been using w/ the initializer .... but actually, we might be able to do this w/ arrays at least in 3.1. It can't conform to a protocol, but the behavior could be there.

Follow up, I'm 82% sure we have this functionality already, might just be different names.

@tanner0101
Copy link
Member Author

Yeah I think it's just the naming right now. Same issue we had with base64 where you can only go Bytes -> String etc.

Sign up for free to subscribe to this conversation on GitHub. Already have an account? Sign in.
Projects
None yet
Development

No branches or pull requests

3 participants