httpclient的webservice客户端与session验证

Java项目集成金蝶ERP SDK实战:Maven依赖管理与核心接口调用 在企业级应用开发中,系统集成是连接不同业务平台、实现数据互通的关键技术。其核心原理在于通过标准化的接口协议(如WebService、RESTful API)和客户端SDK,封装复杂的网络通信、数据序列化与认证逻辑,使开发者能够聚焦于业务逻辑的编排。这项技术的价值在于显著提升开发效率、保障数据交换的准确性与一致性,并降低因接口变更带来的维护成本。典型的应用场景包括企业内部业务系统与ERP(如金蝶、用友)、CRM或财务软件的数据同步。本文聚焦于使用Maven管理Java项目时,如何高效、稳定地集成金蝶云星空官方 阅读详情
httpclient的webservice客户端与session验证
2013-08-17 23:46:22
原创作品,允许转载,转载时请务必以超链接形式标明文章  原始出处 、作者信息和本声明。否则将追究法律责任。 http://observer.blog.51cto.com/4267416/1275608

   欢迎来到:http://observer.blog.51cto.com    

   webservcie是可以跨语言跨平台开发的一种技术,各种计算机语言都可以搭建服务器,同时各种计算机语言也可以开发客户端。只要有服务器,不管是用java还是C++抑或是php搭建的,其他语言都可以根据其开放的wsdl开发好客户端,然后调用其方法就像调用本地本项目的方法一样。
   本文使用httpclient开发客户端,服务器例子依赖于文章:http://observer.blog.51cto.com/4267416/1231205,如果有不明白的可以先看这些文章再看本文。本文在原来例子的基础上加上安全验证与session的使用与权限管理。
   webservice的安全验证有很多方法,实现soapheader认证、集成windows身份验证、ip绑定验证等等。在此博主觉得,基础的,往往却是最有效的。本文使用过滤器验证登录身份,然后就像平时web登录后一样,在session中存放信息达到保持登录与权限的管理。
第一:编写webservice客户端模板
   首先咱们使用httpclient写一个能够访问webservice的客户端,详情可下载源码查看。
   在此,因为wsdl、url、encoding还有就是返回的字段名在后面修改的可能性很大,所以使用配置文件存放他们的信息。

   webservicetest.properties:

1
2
3
4
webservice.wsdl=http://localhost:8080/webServiceCXF/services/Service?wsdl
     webservice.url=http://www.observer.com/service
     webservice.encoding=utf-8
     webservice.fieldname=result

   然后包装一个类读取他们:com.observer.webservcie.util.ServicePropertiesUtil详情可以下载代码查看,咱们说正点。
   在我的上一篇文章:http://observer.blog.51cto.com/4267416/1244274中,介绍了js的webservice客户端的相关内容,其中XMLHttpRequest所起到的作用其实就相当于浏览器访问一个web服务器的作用一样,只不过它访问的时候向服务器推送了一段xml,并且访问的是webservice的url而已。
   既然知道了这个原理,那么跟他一样在java中能够起到浏览器作用的httpclient能不能访问webservice的url进而访问webservice的方法呢?咱们做一下尝试,拭目以待。
   因为后面加上session验证之后,客户端封装就要有所变化,所以在此先将客户端模板写出来,其中发送的xml模板完全可以使用soupui自动生成,soupri的使用参看介绍js的那篇文章。
   TestWebServiceClient:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
public  class  TestWebServiceClient {
         public  static  void  main(String[] args)  throws  FormatException {
             ServicePropertiesUtil servicePropertiesUtil =  new  ServicePropertiesUtil( "webservicetest" );
             //获取读取配置文件的ServicePropertiesUtil类
             StringBuffer sb =  new  StringBuffer();
             sb.append( "<soapenv:Envelope xmlns:soapenv='http://schemas.xmlsoap.org/soap/envelope/' xmlns:ser='" +
                     servicePropertiesUtil.getWebServiceUrl()+ "'>" );
             sb.append( "<soapenv:Header/>" );
             sb.append( "<soapenv:Body>" );
             sb.append( "<ser:getGradeName>" );
             sb.append( "<toid>" ); sb.append( 123 ); sb.append( "</toid>" );
             sb.append( "</ser:getGradeName>" );
             sb.append( "</soapenv:Body>" );
             sb.append( "</soapenv:Envelope>" );
             //访问webservcie时需要用到的xml
                                                          
             HttpClient httpClient =  new  HttpClient(); //新建一个HttpClient类
             PostMethod postMethod= new  PostMethod(servicePropertiesUtil.getWebServiceWsdl());
             postMethod.setRequestHeader( "SOAPAction" , "http://dao.wfservice.ws.emolay.com" );
             String html =  null ;
             try  {
                 String out = sb.toString();
                 postMethod.setRequestEntity( new  StringRequestEntity(out,  "text/xml" ,
                         servicePropertiesUtil.getWebServiceEncoding()));
                 //设置需要推送的数据
                 httpClient.executeMethod(postMethod); //访问webservcie
                 html=postMethod.getResponseBodyAsString(); //获取访问webserivce反馈的xml
                 postMethod.releaseConnection();
             }  catch  (HttpException e) {
                 e.printStackTrace();
                 throw  new  FormatException( "连接异常1" ,  "服务器正在维护中,请稍后再试,或者联系服务器维护人员进行处理" );
             }  catch  (IOException e) {
                 throw  new  FormatException( "连接异常2" ,  "服务器正在维护中,请稍后再试,或者联系服务器维护人员进行处理" );
             }
                                                          
             Document doc=Jsoup.parse(html); //使用jsoup解析xml,得到webservice返回的数据
             Elements elements=doc.select(servicePropertiesUtil.getWebServiceFieldname());
             //根据webservcie的配置,解析xml中的数据
             String [] datas =  new  String[elements.size()];
             int  i =  0 ;
             for (Element ele:elements){
                 datas[i] = ele.text();
                 i++;
             }
                                                          
             //输出数据 
             for (String d : datas){
                 System.out.println(d);
             }
         }
     }

   技术上的东西在注释已经写的很清楚了,这里就不多说了,服务器使用依赖的服务器webServiceCXF,部署服务器到tomcat后,运行这里的main方法,的到结果:“is succeed”;证明客户端代码编写正确,同时也证明了,httpclient是可以访问webservice的。
第二:改造服务器
   首先咱们将服务器改个名,改为:webServiceCXFSession
   在此,也许会有人想,如果在webservice中定义一个登录的方法,webserivce访问这个方法的时候就必须不能被拦截,但是过滤器中是不可能知道你的webservice是要访问什么方法的,只有到了webservice解析完传过来的xml才能知道,这时候就矛盾了,怎么办呢?在此,博主起初是想在传过来的头文件中加上一个参数(如islogin),然后在过滤器中得到这个头文件信息,然后根据这个头文件信息进行判断是否放行。但是这时候又出现问题了,要是别人重写了客户端,把所有的方法传过来的这个islogin全部都改为true,其他都不变,那也可以不用验证就进入webservcie。最后,博主觉得,直接在过滤器中进行判断登录即可,而登录的用户名密码可以使用头文件的形式传过来。
   好了,登录的问题解决了,使用过滤器登录了之后,我们就可以在islogin为false时判断session中是否已经登录了,session中也的确放进了用户信息,但是要怎样才能在webservice的方法中的到session中的信息,进而判断其权限呢?在此就要用到博主的上一篇文章中提到的一个类了,该类为:java.lang.ThreadLocal,简单的解释就是:每个不同线程访问的都是不同的副本(原理上是否这样暂且不管,只要知道达到了这个效果就成),详情可看API或上一篇文章:http://observer.blog.51cto.com/4267416/1263577;我们在访问webservice的过程其实就像访问servlet,以多线程的方式访问,但是一旦进到了服务器,那么访问过滤器与访问webservice的是同一个线程。那么好,只要我们在webservcie实现类中定义一个ThreadLocal,其中放着session,然后在webservcie进入与出来时把session放进与移除,那么在不同用户访问webservcie都可以得到不同的自己的session,然后在方法里面判断其权限即可,如下所示
   GradeServiceImpl中:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
private  static  final  ThreadLocal<HttpSession> threadLocal =
         new  ThreadLocal<HttpSession>();
     public  static  void  setHttpSession(HttpSession session){
         threadLocal.set(session);
     }
     public  static  void  removeSession(){
         threadLocal.remove();
     }
     /**
      * 验证权限,如果不是admin用户,返回状态码"-1"表示没有权限访问该方法
      */
     public  String getGradeName( long  toid) {
         HttpSession session = threadLocal.get();
         String user = (String)session.getAttribute( "user" );
         if ( "admin" .equals(user)){
             System.out.println( "业务逻辑" );
         } else {
             return  "-1" ;
         }
         return  "is succeed" ;
     }

   然后在web.xml中添加过滤器:

1
2
3
4
5
6
7
8
9
10
<!-- webserivce过滤器 -->
< filter >
     < filter-name >webserviceFilter</ filter-name >
     < filter-class >com.observer.cxf.login.filter.LoginFilter</ filter-class >
</ filter >
< filter-mapping >
     < filter-name >webserviceFilter</ filter-name >
     < url-pattern >/services/*</ url-pattern >
</ filter-mapping >
<!-- webserivce过滤器 end -->

   新建过滤器的实现类:com.observer.cxf.login.filter.LoginFilter:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
public  class  LoginFilter  implements  Filter{
     public  void  destroy() {
     }
     /**
      * 过滤器的过滤方法
      * 当传过来的html头文件中有islogin并且为true时表示用户需要登录,那么就验证登录
      * 当传过来的html头文件中有islogin并且为false时表示用户需要调用webservice,
      * 那么首先验证是否已经登录,如果已经登录就继续,如果没有登录就直接返回notlogin提示用户没有登录
      */
     public  void  doFilter(ServletRequest arg0, ServletResponse arg1,
             FilterChain arg2)  throws  IOException, ServletException {
         HttpServletRequest request = (HttpServletRequest)arg0;
         HttpServletResponse response = (HttpServletResponse)arg1;
         HttpSession session = request.getSession();
         String islogin = request.getHeader( "islogin" );
         if ( "false" .equals(islogin)){ //判断是要登录还是要访问webservice
             String user = (String) session.getAttribute( "user" );
             if (user !=  null ){ //判断是否已经登录
                 GradeServiceImpl.setHttpSession(session);
                 //访问webservice之前将session放到webservice实现类中
                 arg2.doFilter(request, response);
                 GradeServiceImpl.removeSession();
                 //webservice访问完成后移除里面的session
                 return ;
             } else {
                 PrintWriter out = response.getWriter();
                 out.println( "notlogin" );
                 out.flush();
                 out.close();
             }
         } else  if ( "true" .equals(islogin)){
             String username = request.getHeader( "username" );
             String password = request.getHeader( "password" );
             //的到头文件中传过来的username与password
             String user = LoginManger.login(username, password);
             PrintWriter out = response.getWriter();
             if (user!= null ){
                 session.setAttribute( "user" , user);
                 out.println( "islogin" );
             } else {
                 out.println( "notlogin" );
             }
             out.flush();
             out.close();
         }
     }
     public  void  init(FilterConfig arg0)  throws  ServletException {
     }
}

   以上代码中的LoginManger.login(username, password);是登录的业务逻辑管理类,一般要检查数据库,在此就不多做了,详情可下载源码看即可。
第三:封装客户端
   服务器已经写好了,究竟能不能用,写好客户端就知道了。
   在此,博主使用模板模式编写客户端,这样在我们的服务器修改了之后,只要大体上没改,我们就可以只修改实现类就可以了,当然,服务器方法添加了的话,抽象类还是要写的,一般情况下,服务器修改的就是一些配置文件上的东西,这时候,相应的xml就会有所改变,那么你就只要修改实现类就可以了。还有这里使用了可变长参数列表,这样如果服务器的webservice方法要是参数改变了的话,也只要修改实现类中的方法内容即可。
   上代码:
   抽象类com.observer.webservcie.httpclient.WebServiceClient:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
public  abstract  class  WebServiceClient {
     public  static  ServicePropertiesUtil servicePropertiesUtil =  new  ServicePropertiesUtil( "webservice" );
     private  static  String tmpcookies= "" ;
     /**
      * 向webservcie发送请求
      * @param outXml 请求所需要推送的xml数据
      * @return 请求反馈的信息
      * @throws FormatException 当webservice服务器关闭或链接不可以等原因造成请求失败时,
      *  抛出com.observer.webservcie.error.FormatException
      */
     private  String executeMethod(String outXml)  throws  FormatException{
         HttpClient httpClient =  new  HttpClient();
         PostMethod postMethod= new  PostMethod(servicePropertiesUtil.getWebServiceWsdl());
         postMethod.setRequestHeader( "Cookie" , tmpcookies);
         postMethod.setRequestHeader( "islogin" , "false" );
         postMethod.setRequestHeader( "SOAPAction" , "http://dao.wfservice.ws.emolay.com" );
         String html =  null ;
         try  {
             String out = outXml;
             postMethod.setRequestEntity( new  StringRequestEntity(out,  "text/xml" ,
                     servicePropertiesUtil.getWebServiceEncoding()));
             httpClient.executeMethod(postMethod);
             html=postMethod.getResponseBodyAsString();
         }  catch  (HttpException e) {
             e.printStackTrace();
             throw  new  FormatException( "连接异常1" ,  "服务器正在维护中,请稍后再试,或者联系服务器维护人员进行处理" );
         }  catch  (IOException e) {
             throw  new  FormatException( "连接异常2" ,  "服务器正在维护中,请稍后再试,或者联系服务器维护人员进行处理" );
         } finally {
             postMethod.releaseConnection();
         }
         return  html;
     }
     /**
      * 向webservcie服务器发送登录请求
      * @param username 用户名
      * @param password 用户密码
      * @return 登录成功后返回服务器反馈的信息:islogin
      * @throws FormatException 当webservice服务器关闭或链接不可以等原因造成请求失败或登录失败时,
      *  抛出com.observer.webservcie.error.FormatException
      */
     public  String login(String username, String password)  throws  FormatException{
         HttpClient httpClient =  new  HttpClient();
         PostMethod postMethod= new  PostMethod(servicePropertiesUtil.getWebServiceWsdl());
         postMethod.setRequestHeader( "islogin" , "true" );
         postMethod.setRequestHeader( "username" ,username);
         postMethod.setRequestHeader( "password" ,password);
         String html =  null ;
         try  {
             httpClient.executeMethod(postMethod);
             html=postMethod.getResponseBodyAsString();
             if (html!= null  &&  "notlogin" .equals(html.trim())){
                 throw  new  FormatException( "登录失败" ,  "用户名密码错误" );
             }
             Cookie[] cookies = httpClient.getState().getCookies();
             StringBuffer sb =  new  StringBuffer();
             for  (Cookie c : cookies) {
                 sb.append(c.toString() +  ";" );
             }
             synchronized ( this ){
                 tmpcookies = sb.toString();
             }
         }  catch  (HttpException e) {
             e.printStackTrace();
             throw  new  FormatException( "连接异常1" ,  "服务器正在维护中,请稍后再试,或者联系服务器维护人员进行处理" );
         }  catch  (IOException e) {
             throw  new  FormatException( "连接异常2" ,  "服务器正在维护中,请稍后再试,或者联系服务器维护人员进行处理" );
         } finally {
             postMethod.releaseConnection();
         }
         return  html;
     }
     /**
      * 将服务器反馈回来的xml解析出结果来
      * @param xml 服务器返回的xml
      * @return 解析出来的结果集
      */
     private  String[] parseData(String xml){
         Document doc=Jsoup.parse(xml);
         Elements elements=doc.select(servicePropertiesUtil.getWebServiceFieldname());
         String [] datas =  new  String[elements.size()];
         int  i =  0 ;
         for (Element ele:elements){
             datas[i] = ele.text();
             i++;
         }
         return  datas;
     }
     /**
      * 想webservice方式请求,并且解析webservice反馈的xml得到结果
      * @param outXml 需要请求发送的xml
      * @return 返回webservice反馈的xml解析之后的结果
      * @throws FormatException 当用户没有登录或者
      * 服务器已经关闭时抛出com.observer.webservcie.error.FormatException
      */
     public  String[] send(String outXml)  throws  FormatException{
         String xml = executeMethod(outXml);
         if ( "notlogin" .equals(xml.trim())){
             throw  new  FormatException( "登陆异常" ,  "对不起您没有登录" );
         }
         return  parseData(xml);
     }
     /**
      * 获取webservice中getGradeName方法所需要的xml的抽象方法,该方法让子类重写,
      * 让其可以在服务器参数更改是灵活的更改
      * @param data 获取webservice中getGradeName所需要的参数
      * @return webservice中getGradeName方法所需要的xml
      * @throws FormatException 当参数不符合规则时
      * 抛出com.observer.webservcie.error.FormatException
      */
     public  abstract  String getGradeNameXml(String... data)  throws  FormatException;
     /**
      * 想webservice请求getGradeName方法的模板方法
      * @param data 获取webservice中getGradeName所需要的参数
      * @return 返回webservice的getGradeName方法返回的数据
      * @throws FormatException 当连接失败或者没有登录或者没有那个权限进行访问该方法时
      * 抛出com.observer.webservcie.error.FormatException
      */
     public  String[] getGradeName(String... data)  throws  FormatException{
         String outXml = getGradeNameXml(data);
         String[] datas = send(outXml);
         if (datas.length> 0  &&  "-1" .equals(datas[ 0 ])){
             throw  new  FormatException( "操作异常" ,  "对不起你没有权限进行此操作" );
         }
         return  datas;
     }
}

   实现类:com.observer.webservcie.httpclient.impl.WebServiceClientImpl:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
public  class  WebServiceClientImpl  extends  WebServiceClient {
         /**
          * 获取webservice中getGradeName方法所需要的xml的实现方法
          * @param data 获取webservice中getGradeName所需要的参数
          * @return webservice中getGradeName方法所需要的xml
          * @throws FormatException 当参数不符合规则时
          * 抛出com.observer.webservcie.error.FormatException
          */
         public  String getGradeNameXml(String... toid)  throws  FormatException{
             int  id;
             try {
                 id = Integer.valueOf(toid[ 0 ]);
             } catch  (Exception e) {
                 throw  new  FormatException( "参数错误" , "输入的参数必须为整数字符串" );
             }
             StringBuffer sb =  new  StringBuffer();
             sb.append( "<soapenv:Envelope xmlns:soapenv='http://schemas.xmlsoap.org/soap/envelope/' xmlns:ser='" +
                     servicePropertiesUtil.getWebServiceUrl()+ "'>" );
             sb.append( "<soapenv:Header/>" );
             sb.append( "<soapenv:Body>" );
             sb.append( "<ser:getGradeName>" );
             sb.append( "<toid>" ); sb.append(id); sb.append( "</toid>" );
             sb.append( "</ser:getGradeName>" );
             sb.append( "</soapenv:Body>" );
             sb.append( "</soapenv:Envelope>" );
             return  sb.toString();
         }
     }

   以上代码中,因为登录跟访问webservice是两个不同的与代码,所以写了两个连接webservice的方法,然后,因为不同的httpclient访问服务器都会产生不同的session,解决的办法就是将上一次访问的Cookie传到下一次访问的httpclient中,这样服务器就会认为你这一次访问的依然是同一个session;在此,用户登录过后,就会将cookie的有关信息存放在一个静态的变量(tmpcookies)中,然后如果下次要进行访问,就将这个变量的cookie放到httpclient的头文件中,让服务器知道你需要使用刚才的session进行访问。
第四:测试
   好了,服务器跟客户端都已经编写完毕,该测试一下了,先登录后访问,不登录就访问等等:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
public  class  TestClient {
     public  static  void  main(String[] args) {
         WebServiceClient webServiceClient =  new  WebServiceClientImpl();
         String[] datas1 =  null ;
         String[] datas2 =  null ;
         try  {
             String login = webServiceClient.login( "admin" ,  "admin" );
             System.out.println(login);
             datas1 = webServiceClient.getGradeName( "123" );
             datas2 = webServiceClient.getGradeName( "2222" );
         }  catch  (FormatException e) {
             e.printStackTrace();
             System.out.println(e.getDetails());
             return ;
         }
         for (String data : datas1){
             System.out.println(data);
         }
         for (String data : datas2){
             System.out.println(data);
         }
     }
}

   在此,博主测试是通过的,如果哪位朋友修改客户端测出了bug,可以给在下个信息,咱们看看能否解决。
第五:打包客户端
   详细的打包客户端这里就不说了,因为在这一篇文章已经有了:http://observer.blog.51cto.com/4267416/1238972,不明白的可以参看它后面的打包测试。
   在这里要说明的是,因为这里的客户端用到了第三方依赖包,所以,你可以直接将依赖包一起打进自己的jar中,但是如果这样做的话,当别人导进你的客户端的同时也导进了依赖包的话就会出现冲突,所以,一般是写一个说明文档,说明该客户端依赖于什么什么第三方的包,想要使用此客户端必须在项目下导进第三方的包,然后将所需要的包列出来,在自己压缩出来的压缩包中也像其他如ssh的框架一样将依赖包也一起放进去。
   到了这里使用httpclient制作客户端与使用session进行用户的验证的方法就已经完成了,详细的可以下载附件代码查看。
   在此,博主是在maven的服务器的项目下进行改造的,因为使用jar包实在是太大,上传实在太慢了,所以有不会用maven的朋友,实在是抱歉了,不过相信能够做java到这一步的,看着本文都能够自己写出项目了,把项目中的代码跟配置移植到普通web项目应该更是没有问题的。

本文出自 “观察者*奔放” 博客,请务必保留此出处http://observer.blog.51cto.com/4267416/1275608

Java安全漏洞攻防实战:SQL注入、XXE、SSRF、RCE原理与修复 在软件开发领域,应用安全是保障系统稳定与数据隐私的基石。其核心原理在于对用户输入进行可信验证,防止恶意数据篡改程序逻辑或访问未授权资源。从技术价值看,构建安全的代码能有效抵御攻击,避免数据泄露、服务中断等风险,这在金融、电商等涉及敏感信息的应用场景中尤为重要。具体到Java工程实践,开发者常面临SQL注入、XXE(XML外部实体攻击)、SSRF(服务端请求伪造)和RCE(远程代码执行)等高频威胁。例如,SQL注入通过拼接未经验证的用户输入改变查询语义;而XXE漏洞则源于XML解析器不当配置,可能引发敏感信息 阅读详情

相关推荐

WebService中Session的使用.zip

webservice服务中如果保持Session 调用Session 对于Web Service,每个方法的调用都会启动一个Session,可以用下面的方法来使多个调用在同一个Session里 CWSSyscfg cwsCfg = new CWSSyscfg(); cwsCfg.CookieContainer = new System.Net.CookieContainer(); CWSSyscfg是一个Web Service类,Web Service的给代理类设置CookieContainer属性,只要多个代理的CookieContainer属性是相同的值, 则对这些Web Service的调用在同一个Session。可以用单例模式来实现。 一般的webservice session 是由cookie 保持的 在两次访问之间保持一个cookie 上下文 就可以保持一个session 所以你需要把前一次返回的结果的http头中 cookie 的所有内容 作为下一次发送你request http头的cookie内容就可以保持session上下文了

在webservice中使用session

1.需要在服务端的方法中加入[WebMethod(EnableSession=true)]修饰方法, 2.在客户端,要在实例化了webservice代理类之后,要为它的CookieContainer 实例化一个 new CookieContainer(); 这样才能使用session存储状态。 3.另外在多个webservice代理中,只要含有相同的cookie,就能共用相同的session

米老头的博客 1289

2022-04-06 RK3566 上调试百兆以太网卡YT8512C 调试记录

一、原理图 二、dts &gmac1_clkin{ clock-frequency = <50000000>; status = "okay"; }; &gmac1 { phy-mode = "rmii"; clock_in_out = "input"; snps,reset-gpio = <&gpio4 RK_PC2 GPIO_ACTIVE_LOW>; snps,reset-active-low; sn...

海月汐辰 1万+

Axis2的会话管理(译)

    本文是对《Axis2 Session Management》的翻译,所依据的英文在http://www.developer.com/services/article.php/3620661/Axis2-Session-Management.htm。以下是翻译内容。     Web服务有着很大的需求,很多人进入了Web服务这一领域,其结果是人们需要Web服务具有更多的特性,以便使用W

滔滔江水的技术博客 2060

关于笔记本测试的面试准备 2021-10-11

** 关于笔记本测试的面试准备 ** 一、根据JD分析,工作内容以软测为主,硬件知识需要了解一点。 以下几个问题为主要: 1.了解VGA、audio、wlan、bt、TP 、camera等driver,BIOS和image测试。 2.了解性能测试工具?压力测试相关设置? 3.了解preload流程? 二、解决 VGA: video graphics array ——笔记本上外接显示器的接口。 【VGA接口兼容性更强,但是不支持高分辨率。 支持高分辨率:HDMI、DIV、TP】 bt【Bluetooth

xw_009的博客 1867

【WRF理论第十五期】WPS中输入geogrid二进制格式

WPS中输入geogrid二进制格式

WW、forever的博客 1080

WebServices 使用Session

using System;using System.Collections.Generic;using System.Data;using System.Linq;using System.Web;using System.Web.Services; namespace LTEServices{ /// <summary> /// HandoverService...

banxieguan5970的博客 180

Open3D 点云变换【2025最新版】

点云平移、旋转、缩放、欧式变换的python代码实现。博客长期更新,本文最近更新时间为:2025年1月16日。

点云侠的博客 37万+

WebService大讲堂之Axis2(5):会话(Session)管理

WebService给人最直观的感觉就是由一个个方法组成,并在客户端通过SOAP协议调用这些方法。这些方法可能有返回值,也可能没有返回值。虽然这样可以完成一些工具,但这些被调用的方法是孤立的,当一个方法被调用后,在其他的方法中无法获得这个方法调用后的状态,也就是说无法保留状态。 读者可以想象,这对于一个完整的应用程序,无法保留状态,就意味着只依靠WebService很难完成全部的工作。例如,...

weixin_33890499的博客 208

Python 爬虫实战:深入闲鱼平台,抓取二手好物价格波动数据

本文介绍了如何利用Python爬虫抓取闲鱼(Xianyu)二手交易平台的商品价格数据并分析其波动趋势。通过requests和BeautifulSoup库实现网页数据抓取与解析,使用pandas进行数据清洗和存储,最后借助matplotlib可视化价格波动情况。文章详细展示了从网页结构分析、数据采集到波动率计算和趋势可视化的完整流程,并建议通过定时任务实现持续数据更新。该项目能为二手市场交易者提供价格参考,帮助优化买卖决策。

专注于Python爬虫开发,分享爬虫技巧、项目实战与反爬经验,使用Scrapy、BeautifulSoup等工具,解决数据抓取难题。 3377

【Charge】仿真目录

Author: JiJi\textrm{Author: JiJi}Author: JiJi Created Time: 2026.01.20\textrm{Created Time: 2026.01.20}Created Time: 2026.01.20 Modified Time: 2026.01.20\textrm{Modified Time: 2026.01.20}Modified Time: 2026.01.20工作流程材料模型[Charge] 电荷分布与折射率变化理论 [Charge] FDTD

u011699626的博客 317

android获取web服务器端session并验证登陆

传统网页实现用户登陆一般采用session或cookie记录用户基本信息又或者两者结合起来使用。android也可以采用session实现用户登陆验证并记录用户登陆状态时的基本信息,session是在服务器端的;而类似cookie的记录方式,则可以在客户端采用xml文件记录用户基本信息,重要数据则可以加密存放客户端。android实现的session登陆功能与网页请求不同的是,网页形式的一次成功的

4053

具身智能(26):RDK S100的LeRobot或Agile X piper机械臂控制模型

本文档详细介绍了基于ROS2的机器人控制模型架构与标定数据联动机制。核心采用"感知-规划-控制"闭环流程,通过激光雷达、相机和IMU的融合数据实现厘米级定位(≤1cm)。文档包含两大控制模型配置:1)RDKLeRobot模型,重点说明PID参数调节和标定文件路径设置;2)AgileXPiper模型,强调驱动安装与外部标定文件集成。针对常见问题提供解决方案,如控制指令无响应需验证标定路径,运动偏差过大需重新标定等。最后给出批量部署方案,通过复制基准配置文件实现多机器人快速配置,要求定位偏差

码农17年的博客 179

SSO单点登陆基于Session简单实现

SSO单点登陆基于Session简单实现 单点登陆活动图 废话不多说直接上代码咯,什么好处,实现原理相关资料baidu去,基本都一样,就不复制了 1 服务端代码 1.1 登陆跳转注销代码 controller层代码 package com.ffcs.sso.controller; import javax.servlet.http.HttpSession; import or...

Sadlay的博客 1269

【OpenClaw企业级智能体实战】第32篇:政企版OpenClaw安全落地指南——奇安信55页报告深度拆解与实战

2026年Q2,OpenClaw(俗称“龙虾”)安全风险集中爆发,公安部、工信部等监管机构密集发声,23万公网暴露实例、155个高危漏洞让企业“养虾”安全压力骤增。奇安信发布的55页《政企版龙虾安全使用指南》,以“看得清、管得住、用得好”为核心,构建了“端-网-云”三层防护体系。本文深度拆解这份报告的九大安全面与三大趋势,全景扫描奇安信、腾讯、360等头部厂商安全方案,提炼企业最低安全基线与实操配置,通过金融机构虚拟案例演示落地全流程,提供从资产摸底、规范制定到工具部署的完整解决方案。

专注于人工智能、软件开发、工控自动化、工厂数字化及智能化等领域,希望和大家共同进步! 575

ET2012新版免狗免安装绿色软件

ET2012新版免狗免安祖昂绿色软件。,新界面,新视觉,

async/await在Web请求中的底层原理与实战避坑指南

async/await并非语法糖,而是基于IO等待特性的线程调度机制,其核心在于释放工作线程以提升Web服务器吞吐量。原理上依赖于真正的异步IO(如HttpClient.GetAsync、EF Core的ToListAsync)而非Task.Run伪异步;技术价值体现在将线程占用从800ms级IO等待压缩至百毫秒级CPU处理,使有限线程池支撑数倍并发。典型应用场景包括高并发API接口、电商详情页、实时日志推送等Web服务。本文聚焦.NET Web开发中async/await的三大陷阱:同步阻塞(.Resul

unixboy 392

复分析 阿尔福斯(Ahlfors) 第三版答案 英文

答案分为十章,有部分习题没有答案,全英文复分析阿尔福斯(Ahlfors) 第三版答案

软件测试应届生求职指南:从自动化测试项目到面试通关全攻略

软件测试是软件研发链路中的关键环节,它通过系统化的验证手段确保产品质量与上线风险可控。随着工程化实践深入,测试开发与自动化测试成为提升效率的核心方式,接口测试、pytest框架、持续集成等技术被广泛应用。对于计算机相关专业的应届生而言,掌握Linux、SQL、Python及HTTP协议等基础,并结合实际的接口自动化测试项目,能够快速构建测试岗位的核心竞争力。从功能测试到测试开发,职业路径清晰且成长空间广阔。本文围绕测试岗位认知、技术栈准备、简历项目打磨、高频面试考点及实战案例,系统梳理了从投递到入职的完整路

weixin_34194087的博客 348

pscad IEEE标准系统搭建说明

pscad IEEE标准系统搭建说明,包含典型的IEEE 9节点、14节点、30节点、39节点和118节点系统。内含标准测试系统的原始数据和潮流结果。

温度PID控制PLC程序

温度PID稳定控制程序,适用于欧姆龙PLC,对其他PLC也具有很大参考价值

Web相关工具和框架

如下所示,我们的服务首先向Dubbo的注册中心进行注册(发送服务的IP、端口、接口方法),消费者向注册中心订阅服务(发送所求的服务信息)以发现服务,注册中心根据消费者所求服务信息匹配对应的提供者列表给消费者,然后消费者从服务提供者地址列表中,基于软负载均衡算法选一台服务提供者进行调用。Dubbo:A服务能提供3种服务功能(接口),B服务能提供4种服务功能,C服务能提供5种服务功能,A服务也许需要使用B服务的功能,B服务需要使用C服务的功能,那让我们组合一波服务搞点事情吧。

milanleon的专栏 434

.NET Framework 1.0到4.0演进中的真实技术契约与迁移避坑指南

.NET Framework 是 Windows 平台企业级应用的底层运行基石,其核心由 CLR 运行时、BCL 类库和配置模型共同构成。从 1.0 到 4.0 的演进并非简单功能叠加,而是经历了四次底层契约重写:泛型引入重构 JIT 行为、CAS 安全模型确立权限边界、WCF/WPF 等技术整合带来跨组件互操作约束,以及 CLR 4.0 的并行运行时机制。这些变更深刻影响着程序集加载、ViewState 序列化、WCF 配置兼容性与 GAC 版本共存等关键环节。尤其在遗留系统迁移中,.NET Framew

416

.NET 2.0升级到3.5 + VS 2008的实战决策与成本权衡

.NET Framework 是微软企业级应用的核心运行时,其版本迁移本质是技术债管理与系统可持续性工程。从.NET 2.0到3.5并非简单语法升级,而是首次在保持CLR 2.0二进制兼容前提下,集成LINQ、WCF、WPF等关键现代化能力的分水岭。该升级显著降低遗留系统维护成本,提升开发人效与调试确定性,尤其适用于政务、金融、制造等仍在运行Windows Server 2003/VS 2005的老旧生产环境。它不改变架构范式,却为后续向.NET 4.0+演进铺平道路,是风险可控、投入产出比极高的‘最小必要

SailingAptech的专栏 529

C#WebService 之Session之我见

这几天一直在学习WebService的知识。正好现在有一个项目,需要在WebService实现如下接口:  String Login(string username, string password) // 登录方法,返回值用来指名是不是登录成功,并且这个值在之后的接口中用来

示申 言舌 的专栏 1万+

httpclient连接webservice

htppclient调用webservice

qq_36437991的博客 1252

WebService之CXF使用Session

[b]一、接口与实现[/b] [code="java"] @WebService public interface IUserLogin { public boolean login(String userId, String password); public boolean logout(String userId); public boolean checkL...

log_cd的专栏 929

在WebService中使用Session或Cookie---实现WebService身份验证(客户端是Flex)

现在我们开发一个项目,业务逻辑层全部用WebService,客户端有Flex和Asp.Net,Flex和Asp.Net的所有业务逻辑数据库的访问全部调用WebService中的方法(好象Flex也不能直接对数据库进行访问,所以也只能用WebService),现在就出现问题了,就是WebService中的权限问题了,比如:我在WebService中有一个Login的方法,还有一个Chang...

weixin_30376083的博客 382

WebService详解

WebService 是一种跨编程语言和跨操作系统平台的远程调用技术。所谓跨编程语言和跨操作平台,就是说服务端程序采用 java 编写,客户端程序则可以采用其他编程语言编写,反之亦然!跨操作系统平台则是指服务端程序和客户端程序可以在不同的操作系统上WebService 是一种标准化的网络服务,允许不同平台和应用程序之间通过网络进行通信。它使得不同语言和平台的应用能够互操作。以下是 WebService 的详细介绍,包括基本概念、类型、工作原理以及应用场景。

刘皇叔说Java的博客 1950
上一篇: Java:Session详解
下一篇: HttpClient 4.0 保持登录session 访问网页
lcathm
博客等级 码龄18年 37粉丝 44原创
评论
成就一亿技术人!
拼手气红包6.0元
还能输入1000个字符
 
 条评论被折叠 查看
添加红包

请填写红包祝福语或标题

个

红包个数最小为10个

元

红包金额最低5元

当前余额3.43元 前往充值 >
需支付:10.00元
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付元
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值