前话说一句:conn.setDefaultRequestProperty(key, value);这个函数是设置属性的,其实可以没有!
 
自己写了一个简单的get,容易控制
public static String callURLtoGet(String strURL) {
try {

            URL url = new URL(strURL);

//            BufferedReader receiver = new BufferedReader(new InputStreamReader(url.openStream()));

            BufferedReader receiver = new BufferedReader(new InputStreamReader(url.openConnection().getInputStream()));

            StringBuffer msg = new StringBuffer();

            char[] data = new char[512];

            int n = 0;

            while ((n = receiver.read(data, 0, 512)) != -1) {

                msg.append(data, 0, n);

            }

            return msg.toString().trim();

        } catch (Exception e) {

            e.printStackTrace();

            return "sdjfaijsdfoiajfjasklfqwh";

        }
}
 
post比较麻烦

public static String sendPost(String strURL) throws Exception {

        URL url = new URL(strURL);

        String result = "";

try {

            HttpURLConnection conn = (HttpURLConnection) url.openConnection();

            conn.setDoOutput(true);

            conn.setDoInput(true);

            conn.setRequestMethod("POST");

            // PrintWriter out = new

            // PrintWriter(httpConn.getOutputStream());//PrintWriter一个打印输出类0,不会自动进行flush和close,继承writer,有多少字符就写多少。

            // 不同于PrintStream类,如System.out这个对象,虽然输出都是write(),但PrintStream会自动进行flush和close,使用outputstream类。

conn.setUseCaches(false);

// conn.setFollowRedirects(true);

            conn.setInstanceFollowRedirects(true);

//            String key = "campaigns";

//            String value = "json";

//            conn.setDefaultRequestProperty(key, value);

            // conn.connect();//

            DataOutputStream out = new DataOutputStream(conn.getOutputStream());// getOutputStream()中隐含的进行了conn.connect;

            // 有乱码可能有问题value;

//            String content = "campaigns=" + "{\"

            JSONObject campaignInfoJSON = new JSONObject();

            campaignInfoJSON = JSONObject.fromObject(content);

            content = "campaigns=" + campaignInfoJSON.toString();

//            content = "campaigns=" + content;

            out.writeBytes(content);

            out.flush();

            out.close();

BufferedReader receiver = new BufferedReader(new InputStreamReader(

                    conn.getInputStream()));

            String line;

            while ((line = receiver.readLine()) != null) {

                result += line;

            }

            receiver.close();

            conn.disconnect();

        } catch (Exception e) {

            e.printStackTrace();

            System.out.println("没有结果!" + e);

        }

// try{

        // URL httpurl = new URL(url);

        // HttpURLConnection httpConn =

        // (HttpURLConnection)httpurl.openConnection();

        // httpConn.setDoOutput(true);

        // httpConn.setDoInput(true);

        // PrintWriter out = new

        // PrintWriter(httpConn.getOutputStream());//PrintWriter一个打印输出类0,不会自动进行flush和close,继承writer,有多少字符就写多少。

        // 不同于PrintStream类,如System.out这个对象,虽然输出都是write(),但PrintStream会自动进行flush和close,使用outputstream类。

        // out.print(param);

        // out.flush();

        // out.close();

        // BufferedReader in = new BufferedReader(new

        // InputStreamReader(httpConn.getInputStream()));

        // String line;

        // while ((line = in.readLine())!= null)

        // {

        // result += line;

        // }

        // in.close();

        // }catch(Exception e){

        // System.out.println("没有结果!"+e);

        // }

        return result;

    }

 
 
 
自己懒得写了,引自网上一个说明,具体说明各个步骤中,函数的内容: 
最常用的Http请求无非是get和post,get请求可以获取静态页面,也可以把参数放在URL字串后面,传递给servlet,post与get的不同之处在于post的参数不是放在URL字串里面,而是放在http请求的正文内。

在Java中可以使用HttpURLConnection发起这两种请求,了解此类,对于了解soap,和编写servlet的自动测试代码都有很大的帮助。

下面的代码简单描述了如何使用HttpURLConnection发起这两种请求,以及传递参数的方法:

publicclass
HttpInvoker...{



public
static
final String GET_URL=
"http://localhost:8080/welcome1";



public
static
final String POST_URL=
"http://localhost:8080/welcome1";



public
static
void readContentFromGet()throws IOException...{

// 拼凑get请求的URL字串,使用URLEncoder.encode对特殊和不可见字符进行编码

String getURL= GET_URL
+ "?username="

+ URLEncoder.encode("fat
man","utf-8");

URL getUrl=
new URL(getURL);

// 根据拼凑的URL,打开连接,URL.openConnection函数会根据URL的类型,

// 返回不同的URLConnection子类的对象,这里URL是一个http,因此实际返回的是HttpURLConnection

HttpURLConnection connection= (HttpURLConnection)
getUrl

.openConnection();

// 进行连接,但是实际上get request要在下一句的connection.getInputStream()函数中才会真正发到

// 服务器

connection.connect();

// 取得输入流,并使用Reader读取

BufferedReader reader=
new BufferedReader(new InputStreamReader(

connection.getInputStream()));

System.out.println("=============================");

System.out.println("Contents of get request");

System.out.println("=============================");

String lines;

while
((lines= reader.readLine())!=
null)...{

System.out.println(lines);

}

reader.close();

// 断开连接

connection.disconnect();

System.out.println("=============================");

System.out.println("Contents of get request ends");

System.out.println("=============================");

}



public
static
void readContentFromPost()throws IOException...{

// Post请求的url,与get不同的是不需要带参数

URL postUrl=
new URL(POST_URL);

// 打开连接

HttpURLConnection connection= (HttpURLConnection)
postUrl

.openConnection();

// Output to the connection. Default is

// false, set to true because post

// method must write something to the

// connection

// 设置是否向connection输出,因为这个是post请求,参数要放在

// http正文内,因此需要设为true

connection.setDoOutput(true);

// Read from the connection. Default is true.

connection.setDoInput(true);

// Set the post method. Default is GET

connection.setRequestMethod("POST");

// Post cannot use caches

// Post 请求不能使用缓存

connection.setUseCaches(false);

// This method takes effects to

// every instances of this class.

// URLConnection.setFollowRedirects是static函数,作用于所有的URLConnection对象。

// connection.setFollowRedirects(true);



// This methods only

// takes effacts to this

// instance.

// URLConnection.setInstanceFollowRedirects是成员函数,仅作用于当前函数

connection.setInstanceFollowRedirects(true);

// Set the content type to urlencoded,

// because we will write

// some URL-encoded content to the

// connection. Settings above must be set before connect!

// 配置本次连接的Content-type,配置为application/x-www-form-urlencoded的

// 意思是正文是urlencoded编码过的form参数,下面我们可以看到我们对正文内容使用URLEncoder.encode

// 进行编码

connection.setRequestProperty("Content-Type",

"application/x-www-form-urlencoded");

// 连接,从postUrl.openConnection()至此的配置必须要在connect之前完成,

// 要注意的是connection.getOutputStream会隐含的进行connect。

connection.connect();

DataOutputStream out=
new DataOutputStream(connection

.getOutputStream());

// The URL-encoded contend

// 正文,正文内容其实跟get的URL中'?'后的参数字符串一致

String content=
"firstname="+ URLEncoder.encode("一个大肥人","utf-8");

// DataOutputStream.writeBytes将字符串中的16位的unicode字符以8位的字符形式写道流里面

out.writeBytes(content);



out.flush();

out.close();// flush and close

BufferedReader reader=
new BufferedReader(new InputStreamReader(

connection.getInputStream()));

String line;

System.out.println("=============================");

System.out.println("Contents of post request");

System.out.println("=============================");

while
((line = reader.readLine())!=
null)...{

System.out.println(line);

}

System.out.println("=============================");

System.out.println("Contents of post request ends");

System.out.println("=============================");

reader.close();

connection.disconnect();

}



/**
*//**

*@param args

*/

public
static
void main(String[] args)...{

// TODO Auto-generated method stub

try
...{

readContentFromGet();

readContentFromPost();


} catch (IOException e)...{

// TODO Auto-generated catch block

e.printStackTrace();

}

}



}

上面的readContentFromGet()函数产生了一个get请求,传给servlet一个username参数,值为"fat man"。

readContentFromPost()函数产生了一个post请求,传给servlet一个firstname参数,值为"一个大肥人"。

HttpURLConnection.connect函数,实际上只是建立了一个与服务器的tcp连接,并没有实际发送http请求。无论是post还是get,http请求实际上直到HttpURLConnection.getInputStream()这个函数里面才正式发送出去。



在readContentFromPost()中,顺序是重中之重,对connection对象的一切配置(那一堆set函数)都必须要在connect()函数执行之前完成。而对outputStream的写操作,又必须要在inputStream的读操作之前。这些顺序实际上是由http请求的格式决定的。



http请求实际上由两部分组成,一个是http头,所有关于此次http请求的配置都在http头里面定义,一个是正文content,在connect()函数里面,会根据HttpURLConnection对象的配置值生成http头,因此在调用connect函数之前,就必须把所有的配置准备好。



紧接着http头的是http请求的正文,正文的内容通过outputStream写入,实际上outputStream不是一个网络流,充其量是个字符串流,往里面写入的东西不会立即发送到网络,而是在流关闭后,根据输入的内容生成http正文。



至此,http请求的东西已经准备就绪。在getInputStream()函数调用的时候,就会把准备好的http请求正式发送到服务器了,然后返回一个输入流,用于读取服务器对于此次http请求的返回信息。由于http请求在getInputStream的时候已经发送出去了(包括http头和正文),因此在getInputStream()函数之后对connection对象进行设置(对http头的信息进行修改)或者写入outputStream(对正文进行修改)都是没有意义的了,执行这些操作会导致异常的发生。

分享到:

java实现http的post和get的更多相关文章

  1. Spark案例分析

    一.需求:计算网页访问量前三名 import org.apache.spark.rdd.RDD import org.apache.spark.{SparkConf, SparkContext} /* ...

  2. 故障重现(内存篇2),JAVA内存不足导致频繁回收和swap引起的性能问题

    背景起因: 记起以前的另一次也是关于内存的调优分享下   有个系统平时运行非常稳定运行(没经历过大并发考验),然而在一次活动后,人数并发一上来后,系统开始卡. 我按经验开始调优,在每个关键步骤的加入如 ...

  3. Elasticsearch之java的基本操作一

    摘要   接触ElasticSearch已经有一段了.在这期间,遇到很多问题,但在最后自己的不断探索下解决了这些问题.看到网上或多或少的都有一些介绍ElasticSearch相关知识的文档,但个人觉得 ...

  4. 论:开发者信仰之“天下IT是一家“(Java .NET篇)

    比尔盖茨公认的IT界领军人物,打造了辉煌一时的PC时代. 2008年,史蒂夫鲍尔默接替了盖茨的工作,成为微软公司的总裁. 2013年他与微软做了最后的道别. 2013年以后,我才真正看到了微软的变化. ...

  5. 故障重现, JAVA进程内存不够时突然挂掉模拟

    背景,服务器上的一个JAVA服务进程突然挂掉,查看产生了崩溃日志,如下: # Set larger code cache with -XX:ReservedCodeCacheSize= # This ...

  6. 死磕内存篇 --- JAVA进程和linux内存间的大小关系

    运行个JAVA 用sleep去hold住 package org.hjb.test; public class TestOnly { public static void main(String[] ...

  7. 【小程序分享篇 一 】开发了个JAVA小程序, 用于清除内存卡或者U盘里的垃圾文件非常有用

    有一种场景, 手机内存卡空间被用光了,但又不知道哪个文件占用了太大,一个个文件夹去找又太麻烦,所以我开发了个小程序把手机所有文件(包括路径下所有层次子文件夹下的文件)进行一个排序,这样你就可以找出哪个 ...

  8. Java多线程基础学习(二)

    9. 线程安全/共享变量——同步 当多个线程用到同一个变量时,在修改值时存在同时修改的可能性,而此时该变量只能被赋值一次.这就会导致出现“线程安全”问题,这个被多个线程共用的变量称之为“共享变量”. ...

  9. Java多线程基础学习(一)

    1. 创建线程    1.1 通过构造函数:public Thread(Runnable target, String name){}  或:public Thread(Runnable target ...

  10. c#与java的区别

    经常有人问这种问题,用了些时间java之后,发现这俩玩意除了一小部分壳子长的还有能稍微凑合上,基本上没什么相似之处,可以说也就是马甲层面上的相似吧,还是比较短的马甲... 一般C#多用于业务系统的开发 ...

随机推荐

  1. python中的printf:%号拼接字符串和format函数

    在C语言中,我们使用printf("%s","hello")这种形式进行字符串的拼接 在python中,进行这样的拼接有两种实现方式,分别是%号拼接以及使用fo ...

  2. python OptParse模块的用法详解

    OptParse模块的简单介绍 Python 有两个内建的模块用于处理命令行参数: 一个是 getopt只能简单处理 命令行参数: 另一个是 optparse,它功能强大,而且易于使用,可以方便地生成 ...

  3. Android进阶 | 摆脱斗图 | 行业交流 | 深度学习 | 付费

    Android进阶 | 摆脱斗图 | 行业交流 | 深度学习 | 付费 其实在很早的时候我就有想过,是不是退出一些群,因为群太多了,里面的水友也多,基友也多,就难免会水起来,这样既耽误学习又耽误工作, ...

  4. Java web文件上传下载

    [版权申明:本文系作者原创,转载请注明出处] 文章出处:http://blog.csdn.net/sdksdk0/article/details/52048666 作者:朱培 ID:sdksdk0 邮 ...

  5. Android6.0 init 深入分析

    之前写过一篇关于android5.0 init的介绍,这篇博客是介绍android6.0init,之前有的代码介绍不详细.而且分析 解析init.rc那块代码也没有结合init.rc介绍. 一. ma ...

  6. 网络爬虫框架Scrapy简介

    作者: 黄进(QQ:7149101) 一. 网络爬虫 网络爬虫(又被称为网页蜘蛛,网络机器人),是一种按照一定的规则,自动地抓取万维网信息的程序或者脚本:它是一个自动提取网页的程序,它为搜索引擎从万维 ...

  7. Web自动化框架LazyUI使用手册(4)--控件抓取工具Elements Extractor详解(批量抓取)

    概述 前面的一篇博文详细介绍了单个控件抓取的设计思路&逻辑以及使用方法,本文将详述批量控件抓取功能. 批量抓取:打开一个web页面,遍历页面上所有能被抓取的元素,获得每个元素的iframe.和 ...

  8. 给定一数组,输出满足2a=b(a,b代表数组中的数)的数对,要求时间复杂度尽量低。

    //时间复杂度O(n),空间复杂度O(n) void findSequence(int* arr, int len) { int* hashtable = new int[RANGE]; memset ...

  9. IE下的deflate模式

    浏览器有一个非常有用的特性:自动解压. 在使用AJAX请求数据的时候,数据在服务器端压缩传输,在浏览器端自动解压,请求直接得到解压后的结果. 在Request Header中,一般会列出浏览器支持的压 ...

  10. Effective C++ ——构造/析构/赋值运算符

    条款五:了解C++默认编写并调用那些函数 是否存在空的类? 假设定义类为class Empty{}:当C++编译器处理过后会变成如下的形式: class Empty{ Empty(){} ~Empty ...