Skip to content

Instantly share code, notes, and snippets.

@downgoon
Last active June 16, 2017 09:48
Show Gist options
  • Save downgoon/ce705bbd48ac764e5129049df74da32a to your computer and use it in GitHub Desktop.
Save downgoon/ce705bbd48ac764e5129049df74da32a to your computer and use it in GitHub Desktop.
vertx confusion

困惑列表

  • JSON
  • Router
  • 函数指针
  • 对象工厂
  • Router : Route = 1 : * , Route : Handler 是 1:1

JSON

  • 对象序列化为JSON
Employee employee = new Employee();
JsonObject.mapFrom(employee).toString()
  • LIST序列化为JSONArray
List<Employee> employees = new ArrayList<Employee>();
new JsonArray(employees).toString();  // 居然不是: JsonArray.mapFrom(employees);
  • JsonObject 与 JavaObject 功能

JsonObject 与 JavaObject 的相互转换

// mapFrom
Employee employee = new Employee();
JsonObject json = JsonObject.mapFrom();

// mapTo
JsonObject jsonObject = new JsonObject();
jsonObject.mapTo(Employee.class);

Router

Vertx vertx = Vertx.vertx();
HttpServer server = vertx.createHttpServer();

// why NOT vertx.createRouter()
Router router = Router.router(vertx);

API风格不统一,但是这里的原因是:HttpServer 是 vertx-core 的, Router 是 vertx-web 的,属于 vertx-core 的拓展。 如果 vertx.createRouter() 则会导致 vertx-core 依赖于 vertx-web

函数指针

server.requestHandler(mainRouter::accept);
  • HttpServer.java
public interface HttpServer {
  HttpServer requestHandler(Handler<HttpServerRequest> handler);
}
  • Router.java
public class Router {
  void accept(HttpServerRequest request);
}

对象工厂

Vertx vertx = Vertx.vertx();  // NOT  Vertx vertx = new Vertx();
Router router = Router.router();  //  NOT Router router = new Router(); 

虽然是工厂模式减少 new 的依赖,但是也不向从前的 Vertx vertx = VertxFactory.newInstance();

Route 与 Handler 是一一对应

Route route = dbapiRouter.route(HttpMethod.POST, "/:dbname/:tableName");
route.handler(routingContext -> {
	System.out.println("同一个对象route 上 第一次执行");
	routingContext.next();
});

route.handler(routingContext -> {
	System.out.println("同一个对象route 上 第二次执行");   // 覆盖前者
	routingContext.next();
});
		
// 以下不会后者覆盖前者,因为它们是三个 Route,只不过三者的 匹配完全相同。		
dbapiRouter.route(HttpMethod.POST, "/:dbname/:tableName").handler(routingContext -> {
	System.out.println("创建前");
	routingContext.next();
});
dbapiRouter.route(HttpMethod.POST, "/:dbname/:tableName").handler(dbapiAction::post);
dbapiRouter.route(HttpMethod.POST, "/:dbname/:tableName").handler(routingContext -> {
	System.out.println("创建后");
});

我刚困惑的是这个: 前面文档说 一个 Router 可以多个 Route, 一个 Route 对应一个 Handler。 然后我写着 dbapiRouter.route().handler(BodyHandler.create()) 和 dbapiRouter.route().handler( rcx -> {….}) ,发现两个都生效了,然后我就困惑了,我的预期是 后者为什么没有覆盖前者 (因为 “一个 Route 对应一个 Handler” ) ? 原因是 dbapiRouter.route() 前后两次其实弄了两个route() 只不过这两个 route 的匹配规则完全一样而已。

@downgoon
Copy link
Author

downgoon commented May 10, 2017

Cookie

vertx.web 为了提高性能,默认情况下是不会解析Cookie的,即便它属于HTTP头的范畴。
需要Cookie时,可以在最前面:

// Vert.x-Web has cookies support using the CookieHandler.
// You should make sure a cookie handler is on a matching route 
  //  for any requests that require this functionality.

router.route().handler(CookieHandler.create());

读写Cookie

servlet 中,读Cookie,是HttpRequest的事;写Cookie,是HttpResponse的事。
而 vertx 中,读写Cookie却直接在 routingContext 上。或许是因为不是所有的请求都处理COOKIE。

router.route().handler(CookieHandler.create());

router.route("some/path/").handler(routingContext -> {

  Cookie someCookie = routingContext.getCookie("mycookie");
  String cookieValue = someCookie.getValue();

  // Do something with cookie...

  // Add a cookie - this will get written back in the response automatically
  routingContext.addCookie(Cookie.cookie("othercookie", "somevalue"));
});

@downgoon
Copy link
Author

downgoon commented May 10, 2017

Curl with Cookies and Headers

06/17/2010 http://joelpm.com/curl/tools/2010/06/17/curl-with-cookies-and-headers.html

Every now and then I find myself needing to make an http request with specific cookies and headers to help debug an issue. And every time I resort to the curl manpage and try a few times until I get the right incantation. So, to save myself time in the future, here is an example:

curl -v --cookie "cookieName=cookieValue" --header "Accept-Language: en" --header "X-Forwarded-For: 123.123.123.123" "http://localhost:8080/somepage"

verbose

-v
Tells curl to be verbose, useful for seeing if your headers are being sent.

add cookie

--cookie "cookieName=cookieValue"
Tells curl to send the cookie header with the given value.

Multiple cookies can be sent using "cookieName1=cookieValue1;cookieName2=cookieValue2".

add header

--header "headerName: headerValue"
Tells curl to add the header line you specified.

You can send multiple headers by giving multiple --header arguments (see above).
The ability to hand-craft HTTP requests is a great feature of curl and makes it a great debugging tool.


example

curl -i -v -X POST --cookie "WG-PPC-UID=1ueIUbXoMNQ.;WG-PPC-MIX=1ueIUbXoMNQ.|0|0|zhangcong00|https://face.com/abc;WG-PPC-CASTOKEN=G6k3M7dMG4lfu24lOG1QruIsAW9PxllfguI8HXFw4Y"  http://localhost:8080/bind/BOX123456
*   Trying ::1...
* TCP_NODELAY set
* Connected to localhost (::1) port 8080 (#0)
> POST /bind/BOX123456 HTTP/1.1
> Host: localhost:8080
> User-Agent: curl/7.51.0
> Accept: */*
> Cookie: WG-PPC-UID=1ueIUbXoMNQ.;WG-PPC-MIX=1ueIUbXoMNQ.|0|0|zhangcong00|https://face.com/abc;WG-PPC-CASTOKEN=G6k3M7dMG4lfu24lOG1QruIsAW9PxllfguI8HXFw4Y
>
< HTTP/1.1 200 OK
HTTP/1.1 200 OK
< Server: boxcloud
Server: boxcloud
< Content-Type: application/json;charset=UTF-8
Content-Type: application/json;charset=UTF-8
< Content-Length: 67
Content-Length: 67

<
* Curl_http_done: called premature == 0
* Connection #0 to host localhost left intact
{"status":200,"message":"bind succ","debug":null,"attachment":null}

@downgoon
Copy link
Author

到处依赖vertx

  • 当我们要读一个文件的时候,需要基于vertx对象才能用;
  • 当我们创建一个HTTP Client的时候,也需要vertx对象。

这种给编程带来很大的不方便。

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment