linugb118--java space

Java

2012年10月18日 #

Javascript端加密java服务端解密

                                   Javascript端加密java服务端解密

 

通常我们会通过htts来保证传输安全,但如果我们不用https,如何通过javascript来保证浏览器端发送的参数进行加密,并且通过RSA算法来处理。

 

这里我们可以利用jquery的一个加密插件jcryption来处理,可以参考

http://jcryption.org/#examples

现在版本是3.0 但是没有java端的实现,下次有时间再研究。现在这个用的是1.1的版本

这个可以在

http://linkwithweb.googlecode.com/svn/trunk/Utilities/jCryptionTutorial 获取

 

不过他的服务端有个缺陷我修改了。

接来大致介绍如下:

 

1.     首先服务端有产生publicKeyservlet

package com.gsh.oauth.auth.servlet;

 

import java.io.IOException;

import java.security.KeyPair;

 

import javax.servlet.ServletException;

import javax.servlet.http.HttpServlet;

import javax.servlet.http.HttpServletRequest;

import javax.servlet.http.HttpServletResponse;

 

import com.gsh.oauth.auth.util.JCryptionUtil;

 

/**

 * Servlet implementation class EncryptionServlet

 */

public class EncryptionServlet extends HttpServlet {

       private static final long serialVersionUID = 1L;

 

       /**

        * Default constructor.

        */

       public EncryptionServlet() {

               // TODO Auto-generated constructor stub

       }

 

       /**

        * @see HttpServlet#service(HttpServletRequest request, HttpServletResponse response)

        */

       protected void service(HttpServletRequest request,

                      HttpServletResponse response) throws ServletException, IOException {

               int KEY_SIZE = 1024;

               if (request.getParameter("generateKeypair") != null) {

 

                      JCryptionUtil jCryptionUtil = new JCryptionUtil();

 

                      KeyPair keys = null;

                      //if (request.getSession().getAttribute("keys") == null) { //这里注释掉 否则第二次请求会500

                             keys = jCryptionUtil.generateKeypair(KEY_SIZE);

                             request.getSession().setAttribute("keys", keys);

                      //}

 

                      StringBuffer output = new StringBuffer();

 

                      String e = JCryptionUtil.getPublicKeyExponent(keys);

                      String n = JCryptionUtil.getPublicKeyModulus(keys);

                      String md = String.valueOf(JCryptionUtil.getMaxDigits(KEY_SIZE));

 

                      output.append("{\"e\":\"");

                      output.append(e);/Files/linugb118/bcprov-jdk15-1.46.jar.zip

                      output.append("\",\"n\":\"");

                      output.append(n);

                      output.append("\",\"maxdigits\":\"");

                      output.append(md);

                      output.append("\"}");

 

                      output.toString();

                      response.getOutputStream().print(

                                    output.toString().replaceAll("\r", "").replaceAll("\n", "")

                                                   .trim());

               } else {

                      response.getOutputStream().print(String.valueOf(false));

               }

       }

 

}

 

2. Client例子

<html>

<head>

<title>Login form</title>

</head>

<meta http-equiv="Content-Type"

    content="text/html; charset=utf-8">

 

<script src="../js/jquery-1.4.2.min.js" type="text/javascript"></script>

<script src="../js/jquery-ui-1.8.2.custom.min.js"

    type="text/javascript"></script>

<script type="text/javascript"

    src="../js/security/jquery.jcryption-1.1.min.js"></script>   

   

<script type="text/javascript">

    $(document).ready(function() {

        var $statusText = $('<span id="status"></span>').hide();

        $("#status_container").append($statusText);

        $("#lf").jCryption({

            getKeysURL:"/gsh/oauth/encryption?generateKeypair=true",

                                        beforeEncryption : function() {

                                            $statusText

                                                   .text("Test Code")

                                                   .show();

                                            return true;

                                        },

                                        encryptionFinished : function(

                                               encryptedString,

                                               objectLength) {

                                            $statusText

                                                   .text(encryptedString);

                                            return true;

                                        }

                                    });

                  });

</script>

<body>

 

<form id="lf" action="/gsh/oauth/authorization"

    method="post">

<fieldset><legend>login</legend>

<div>

<div>client_id:<br>

<input type="text" size="45" name="client_id" value=""></div>

<div>redirect_uri:<br>

<input type="text" size="45" name="redirect_uri" value=""></div>

</div>

<div>loginid:<br>

<input type="text" size="45" name="loginid" value=""></div>

</div>

<div>password:<br>

<input type="password" size="45" name="password" value=""></div>

</div>

<div>

<p><input type="submit" /><span id="status_container"></span></p>

</div>

</fieldset>

</form>

</body>

</html>

 

上面看代码可以看出 他通过/gsh/oauth/encryption?generateKeypair=true来先请求获取public 然后通过jcryption进行加密 然后post到服务端。Encryption就是上面的EncryptionServlet

通过浏览器工具可以看到表单里面的数据加密为

 

jCryption=95f1589502288050e08b4bd8b1a360341cf616d9054531b85a6ef85783c1723b46686ec454ee81f1304fa2370ce24c4d9c06f84d47aa4bdf99310ae12b514db19bfcc325f3a39a584c23b1546550f4e0635c12486f2fd84dec137e1c61cfa775dfa3057a1f0154712aaba0af0cc61810282780f15bed909c24a184e66ab39f2e

3. 目标servletauthorization)的解密

 

public class Authorization extends HttpServlet {

 

    protected void doGet(HttpServletRequest httpServletRequest,

           HttpServletResponse httpServletResponse) throws ServletException,

           IOException {

      

PrintWriter out = httpServletResponse.getWriter();

       

        KeyPair keys = (KeyPair) httpServletRequest.getSession().getAttribute("keys");

        String encrypted = httpServletRequest.getParameter("epCryption");

       

        String client_id = null;

    String redirect_uri = null;

    String loginid = null;

    String password = null;

 

       try {

               String data = JCryptionUtil.decrypt(encrypted, keys);

               httpServletRequest.getSession().removeAttribute("keys");

               Map params = JCryptionUtil.parse(data, "UTF-8");

               client_id = (String) params.get("client_id");

               redirect_uri = (String) params.get("redirect_uri");

               loginid = (String) params.get("loginid");

               password = (String) params.get("password");

 

           } catch (Throwable e) {

               e.printStackTrace();

           }

}

 

    }

 

上面至少片段,需要相关的jsjava问题,请在svn上面获取。另外还需要bcprov-jdk15-1.46.jar

可以在http://mvnrepository.com/artifact/org.bouncycastle/bcprov-jdk15/1.46

获取。

 

 

 

 

posted @ 2014-05-09 10:07 linugb118 阅读(4205) | 评论 (1)编辑 收藏

cas3 设置独立登录页面

在使用cas3的时候,往往有这样的需求,希望每个应用有个独立的登录页面
这块cas 官方文档有一些说明
https://wiki.jasig.org/display/CAS/Using+CAS+without+the+Login+Screen
首先从官方的角度,不建议使用多个登录页面,这样对安全会形成短板。但是
用户需求之上,如果我们要实现,有下面几种方式
1.通过参数来判断css来改变布局甚至一些图片,典型cas里面的default-view中
casLoginView.jsp 里面就有这样的描述,通过描述可以看出他通过不同css来区分
weblogin和mobilelogin。
比如片段
<c:if
test="${not empty requestScope['isMobile'] and not empty mobileCss}">
<meta name="viewport"
content="width=device-width; initial-scale=1.0; maximum-scale=1.0; user-scalable=0;" />
<meta name="apple-mobile-web-app-capable" content="yes" />
<meta name="apple-mobile-web-app-status-bar-style" content="black" />
<!--<link type="text/css" rel="stylesheet" media="screen" href="<c:url value="/css/fss-framework-1.1.2.css" />" />
             <link type="text/css" rel="stylesheet" href="<c:url value="/css/fss-mobile-${requestScope['browserType']}-layout.css" />" />
             <link type="text/css" rel="stylesheet" href="${mobileCss}" />-->
</c:if>
2.cas服务端(或者各种应用中)建立一个独立的form页面
参考:https://wiki.jasig.org/display/CAS/Using+CAS+from+external+link+or+custom+external+form
比如:
在cas(或者各种的应用页面) web-inf/ 页面添加testlogin.html
代码:
<html>
<head />
<body>
    <form method="GET" action="http://192.168.2.109:8080/cas/login">
        <p>Username : <input type="text" name="username" /></p>
        <p>Password : <input type="password" name="password" /></p>
        <p>Remember me : <input type="checkbox" name="rememberMe" value="true" /></p>
        <p><input type="submit" value="Login !" /></p>
        <input type="hidden" name="auto" value="true" />
        <input type="hidden" name="service" value="http://localhost/user/checklogintocas.php" />
    </form>
</body>
</html>
casLoginView.jsp
实现自动提交功能:
...
<%@ page contentType="text/html; charset=UTF-8" %>
<%
String auto = request.getParameter("auto");
if (auto != null && auto.equals("true")) {
%>
<html>
    <head>
        <script language="javascript">
            function doAutoLogin() {
                document.forms[0].submit();
            }
        </script>
    </head>
    <body onload="doAutoLogin();">
        <form id="credentials" method="POST" action="<%= request.getContextPath() %>/login?service=<%= request.getParameter("service") %>"> 
            <input type="hidden" name="lt" value="${loginTicket}" />
            <input type="hidden" name="execution" value="${flowExecutionKey}" />
            <input type="hidden" name="_eventId" value="submit" />
            <input type="hidden" name="username" value="<%= request.getParameter("username") %>" />
            <input type="hidden" name="password" value="<%= request.getParameter("password") %>" />
            <% if ("true".equals(request.getParameter("rememberMe"))) {%>
                <input type="hidden" name="rememberMe" value="true" />
            <% } %>
             
            <input type="submit" value="Submit" style="visibility: hidden;" />
        </form>
    </body>
</html>
<%
} else {
%>
<jsp:directive.include file="includes/top.jsp" />
...
<jsp:directive.include file="includes/bottom.jsp" />
<%
}
%>

3.第三种方法 其实是第二种方法的启发,直接把用if-else 把多个页面组合在一起,通过参数来判断显示。(最好能可以支持多套casLoginView.jsp 不过研究下来好像比较难,也许cas开发者也是为了怕再次开放的人用太多灵活的多套casLoginView.jsp 页面跳来跳去把项目搞混吧。)

posted @ 2013-05-28 17:12 linugb118 阅读(3973) | 评论 (0)编辑 收藏

php的memcached客户端memcached

【转】php的memcached客户端memcached

Tags:  ,  , 
文章作者:Enjoy 转载请注明原文链接。
之前在安装memcache时有提到memcached客户端是叫memcache,其实还有一个基于libmemcached的客户端叫memcached,据说性能更好,功能也更多。

memcache的官方主页:http://pecl.php.net/package/memcache
memcached的官方主页:http://pecl.php.net/package/memcached

以下是我安装Memcached版本的PHP模块的过程记录:

wgethttp://download.tangent.org/libmemcached-0.48.tar.gz
tar zxf libmemcached-0.48.tar.gz
cd libmemcached-0.48
./configure --prefix=/usr/local/libmemcached --with-memcached
make
make install

wget http://pecl.php.net/get/memcached-1.0.2.tgz
tar zxf memcached-1.0.2.tgz
cd memcached-1.0.2
/usr/local/webserver/php/bin/phpize 
./configure --enable-memcached --with-php-config=/usr/local/webserver/php/bin/php-config --with-libmemcached-dir=/usr/local/libmemcached
make
make install

在php.ini中加入
extension=memcached.so
完成

另:
在安装libmemcached时,如果只用./configure,可能会提示:
checking for memcached… no
configure: error: “could not find memcached binary”

两者使用起来几乎一模一样。

    $mem = new Memcache;
    $mem->addServer($memcachehost, '11211');    
    $mem->addServer($memcachehost, '11212');
    $mem->set('hx','9enjoy');
    echo $mem->get('hx');


    $md = new Memcached;
    $servers = array(
        array($memcachehost, '11211'),
        array($memcachehost, '11212')
    );
    $md->addServers($servers);
    $md->set('hx','9enjoy');
    echo $md->get('hx');


memcached的方法比memcache多不少,比如getMulti,getByKey,addServers等。
memcached没有memcache的connect方法,目前也还不支持长连接。
memcached 支持 Binary Protocol,而 memcache 不支持,意味着 memcached 会有更高的性能。
Memcache是原生实现的,支持OO和非OO两套接口并存,memcached是使用libmemcached,只支持OO接口。
更详细的区别:http://code.google.com/p/memcached/wiki/PHPClientComparison


memcached服务端是集中式的缓存系统,分布式实现方法是由客户端决定的。
memcached的分布算法一般有两种选择:
1、根据hash(key)的结果,模连接数的余数决定存储到哪个节点,也就是hash(key)% sessions.size(),这个算法简单快速,表现良好。然而这个算法有个缺点,就是在memcached节点增加或者删除的时候,原有的缓存数据将大规模失效,命中率大受影响,如果节点数多,缓存数据多,重建缓存的代价太高,因此有了第二个算法。
2、Consistent Hashing,一致性哈希算法,他的查找节点过程如下:
    首先求出memcached服务器(节点)的哈希值,并将其配置到0~232的圆(continuum)上。然后用同样的方法求出存储数据的键的哈希值,并映射到圆上。然后从数据映射到的位置开始顺时针查找,将数据保存到找到的第一个服务器上。如果超过2的32次方后仍然找不到服务器,就会保存到第一台memcached服务器上。

memcache在没有任何配置的情况下,是使用第一种方法。memcached要实现第一种方法,似乎是使用(未确认):
$md->setOption(Memcached::OPT_HASH, Memcached::HASH_CRC);   

第二种一致性哈希算法:

memcache在php.ini中加
Memcache.hash_strategy =consistent
Memcache.hash_function =crc32


memcached在程序中加(未确认)
$md->setOption(Memcached::OPT_DISTRIBUTION, Memcached::DISTRIBUTION_CONSISTENT);
$md->setOption(Memcached::OPT_HASH, Memcached::HASH_CRC);   

$mem->setOption(Memcached::OPT_DISTRIBUTION,Memcached::DISTRIBUTION_CONSISTENT);
$mem->setOption(Memcached::OPT_LIBKETAMA_COMPATIBLE,true);

一些参考文档:
memcached分布测试报告(一致性哈希情况下的散列函数选择):http://www.iteye.com/topic/346682
php模块memcache和memcached区别:http://hi.baidu.com/dong_love_yan/blog/item/afbe1e12d22e7512203f2e21.html
PHP模块:Memcached > Memcache:http://hi.baidu.com/thinkinginlamp/blog/item/717cd42a11f6e491023bf67a.html


20110509@@UPDATE:
如果安装libmemcached有如下出错提示:
make[2]: *** [clients/ms_conn.o] Error 1
make[2]: Leaving directory `/www/soft/libmemcached-0.48'
make[1]: *** [all-recursive] Error 1
make[1]: Leaving directory `/www/soft/libmemcached-0.48'
make: *** [all] Error 2

可在configure时增加--disable-64bit CFLAGS="-O3 -march=i686"
即:./configure --prefix=/usr/local/libmemcached --with-memcached --disable-64bit CFLAGS="-O3 -march=i686"

posted @ 2013-03-22 14:19 linugb118 阅读(370) | 评论 (0)编辑 收藏

绿色mysql安装问题

1. windows里面出现“拒绝访问”, 那需要通过管理员身份运行cmd

2. 安装服务时候指定的ini路径需要注意,应该指定你现在mysql目录现有的ini文件
如mysqld --install mysql --defaults-file="C:\MySQL5\my.ini"



posted @ 2013-03-21 10:36 linugb118 阅读(291) | 评论 (0)编辑 收藏

Mulestudio 运行demo出错

现象:
 执行demo,比如helloexample ,点击“run as mule application”,弹出框“Could not find the main class.Program will exit”
控制台出现:
java.lang.NoClassDefFoundError: org/mule/tooling/server/application/ApplicationDeployer
Exception in thread "main" 

解决方法:
 是因为jdk 有问题,在mule官网上要求

Before installing Mule Studio, ensure that the host machine has one of the following Java Development Kit versions installed on it:

  • Standard Edition 1.6.0_26 (also known as JDK SE 6 Update 26) or more recent
  • Enterprise Edition 1.6u3 (JDK EE 6 Update 3) or more recent
  • Any version (SE or EE) of JDK 7
    在java build path--》libraries 选择jre system library 为jdk1.7就可以。

posted @ 2012-10-18 17:22 linugb118 阅读(336) | 评论 (0)编辑 收藏

My Links

Blog Stats

常用链接

留言簿(1)

随笔档案

搜索

最新评论

阅读排行榜

评论排行榜