java安全编码指南之:输入注入injection( 二 )

上面的代码中 , 我们还是自己进行了SQL的拼装 , 虽然最后我们使用了preparedStatement , 但是没有达到效果 。
正确使用的例子如下:
String sqlString ="select * from user where username=? and password=?";PreparedStatement stmt = connection.prepareStatement(sqlString);stmt.setString(1, username);stmt.setString(2, pwd);ResultSet rs = stmt.executeQuery();我们需要将用户输入作为参数set到PreparedStatement中去 , 这样才会进行转义 。
XML中的SQL注入可扩展标记语言(XML)旨在帮助存储 , 结构化和传输数据 。由于其平台独立性 , 灵活性和相对简单性 , XML已在许多应用程序中得到使用 。但是 , 由于XML的多功能性 , 它容易受到包括XML注入在内的各种攻击的攻击 。
那么什么是XML注入呢?我们举个例子:
Iphone205000.01上面的例子中 , 我们使用了XML定义了一个iphone20的价格和数量 。 一个iphone20 5000块 。
上面的XML中 , 如果quantity是用户输入的数据的话 , 那么用户可以这样输入:
120.01最后得出的XML文件如下:
Iphone205000.0120.01一般来说 , 我们在解析XML的过程中 , 如果发现有重复的tag , 那么后面的tag会覆盖前面的tag 。
结果就是1个iphone20现在的价格是20块 , 非常划算 。
XML注入的java代码我们看下XML的注入在java代码中是怎么实现的:
public String createXMLInjection(String quantity){String xmlString = "\nIphone20\n"+ "5000.0\n" + "" + quantity+ "";return xmlString;}可以看到我们直接使用用户输入的quantity作为XML的拼接 , 这样做很明显是有问题的 。
怎么解决呢?有两种方法 。

  • 第一种方法
第一种方法就是对用户输入的quantity进行校验:
public String createXML(String quantity){int count = Integer.parseUnsignedInt(quantity);String xmlString = "\nIphone20\n"+ "5000.0\n" + "" + count+ "";return xmlString;}上面代码中 , 我们对quantity进行了Integer的转换 , 从而避免了用户的非法输入 。
  • 第二种方法
第二种方法是使用XML Schema , 来对生成的XML进行格式校验 。
先看一下我们改怎么定义这个XML Schema:
上面我们定义了一个XML element的序列sequence 。 如果用户输入了非定义格式的其他XML , 就会报错 。
我们看下相对应的java代码该怎么写:
StreamSource ss = new StreamSource(new File("schema.xsd"));Schema schema = sf.newSchema(ss);SAXParserFactory spf = SAXParserFactory.newInstance();spf.setSchema(schema);SAXParser saxParser = spf.newSAXParser();XMLreader reader = saxParser.getXMLReader();reader.setContentHandler(defHandler);reader.parse(xmlStream);上面我们列出了XML验证的代码 , 完整的代码可以参考文末的代码链接 , 这里就不一一贴出来了 。


推荐阅读