2017-01-07 106 views
0

我做了一个PHP rest api。我想通过IOS和Android应用程序连接到API。但我不知道如何保护一切。REST API安全设计

我在数据库中注册的设备时,应用程序大火首次

表设备:

id random enabled 
1 12345 1 

每个设备都有一个ID和一个随机的。随机值在该表中是唯一的。实际的设备收到ID和随机值。

我现在所拥有的:

我确认在PHP端的每个请求:

private function validateUrl(){ 
     $url = $_SERVER['REQUEST_URI']; 
     $signature = isset($_GET['signature']) ? $_GET["signature"] : null; 
     $url = str_replace('&signature=' . $signature, '',$url); 
     $url = "" . $url; 
     $correctSignature = md5($url . "TNynVX9k2HqYSXnd"); 

     if($signature != $correctSignature){ 
      echo die(json_encode([array('status' => "not valid")])); 
     } 
    } 

在(在这种情况下)的要求IOS侧:

private func random() -> Int { 

    var result = ""; 

    for _ in 1...3 { 
     let randomNumber = arc4random_uniform(99) 
     result += String(randomNumber); 
    } 

    return Int(result)!; 
} 

private func md5(string string: String) -> String { 
    var digest = [UInt8](count: Int(CC_MD5_DIGEST_LENGTH), repeatedValue: 0) 
    if let data = string.dataUsingEncoding(NSUTF8StringEncoding) { 
     CC_MD5(data.bytes, CC_LONG(data.length), &digest) 
    } 

    var digestHex = "" 
    for index in 0..<Int(CC_MD5_DIGEST_LENGTH) { 
     digestHex += String(format: "%02x", digest[index]) 
    } 

    return digestHex 
} 

func createUrl(url : String) -> String { 
    var newUrl = url; 
    newUrl += "?&random=\(random())"; 
    let secret = "TNynVX9k2HqYSXnd" 
    let signature = md5(string: newUrl + secret) 

    newUrl += "&signature=" + signature; 

    return newUrl; 
} 

这效果很好,但正如你所看到的我有一个静态的API密钥。我有我的担忧。所以我想也许我可以根据ID创建一个API密钥,并从我的数据库中随机创建一个。更安全吗?

喜欢的东西:

func createUrl(url : String) -> String { 
    var newUrl = url; 

    let signature = md5(string: [device id here] + [device random here]) 

    newUrl += "&signature=" + signature; 
    newUrl += "&deviceId=" + [device id here]; 

    return newUrl; 
} 

而在我的PHP身边,我可以从URL中的DeviceID属性。将它与数据库进行比较,检索id和随机值。 MD5他们。将其与签名进行比较。当有一场比赛没关系的时候。否则不是。这是一个坚实的实施?

或简单地说。我可以用id + random的组合替换api key吗?

回答

1

看起来你使用的是相同的秘密客户端和服务器端,这可能是一个问题,因为任何有权访问* .apk或* .ipa的人都可以反汇编它并找到令牌,这很容易开源工具(https://github.com/iBotPeaches/Apktool)。特别是在Android上,APK几乎是一些其他资源的jar。你是否生成随机令牌客户端?由于它看起来是一个整数,只有32位的熵,不够安全。

通常,令牌是创建服务器端而不是客户端。有很多不同的方式来做到这一点。一种是JSON Web Token(JWT),它基本上将数据编码为一个id或将数据过期到一个用私钥签名的令牌中。只有服务器知道私钥,因此它是创建它们的可信来源,但其他人可以访问可用于验证令牌的公钥。

如果你不想处理JWT的签名,第二个选项就是服务器端创建的不透明令牌。关键是大量的UUID像大量的熵。

关于生成数学关联的公钥/私钥对的非对称算法有很多信息。您可以在这里阅读更多: