diff --git a/mywust-core/src/main/java/cn/linghang/mywust/core/api/Bkjx.java b/mywust-core/src/main/java/cn/linghang/mywust/core/api/Bkjx.java index 384129e..f93e10a 100644 --- a/mywust-core/src/main/java/cn/linghang/mywust/core/api/Bkjx.java +++ b/mywust-core/src/main/java/cn/linghang/mywust/core/api/Bkjx.java @@ -8,7 +8,6 @@ import lombok.Getter; */ @Getter public class Bkjx { - public static final String BKJX_SSO_SERVICE = "http://bkjx.wust.edu.cn/jsxsd/sso.jsp"; public static final String BKJX_SESSION_COOKIE_API = "http://bkjx.wust.edu.cn/jsxsd/sso.jsp?ticket=%s"; public static final String BKJX_TEST_API = "http://bkjx.wust.edu.cn/jsxsd/xxwcqk/xxwcqk_idxOnzh.do"; diff --git a/mywust-core/src/main/java/cn/linghang/mywust/core/api/Library.java b/mywust-core/src/main/java/cn/linghang/mywust/core/api/Library.java new file mode 100644 index 0000000..fa31aca --- /dev/null +++ b/mywust-core/src/main/java/cn/linghang/mywust/core/api/Library.java @@ -0,0 +1,9 @@ +package cn.linghang.mywust.core.api; + +public class Library { + public static final String LIBRARY_SESSION_COOKIE_API = "https://libsys.wust.edu.cn/meta-local/opac/cas/rosetta?ticket=%s"; + + public static final String LIBRARY_INDEX_URL = "https://libsys.wust.edu.cn/meta-local/opac/cas/rosetta"; + + public static final String LIBRARY_COOKIE_TEST_URL = "https://libsys.wust.edu.cn/meta-local/opac/users/info"; +} diff --git a/mywust-core/src/main/java/cn/linghang/mywust/core/api/UnionAuth.java b/mywust-core/src/main/java/cn/linghang/mywust/core/api/UnionAuth.java index f6778dd..93f7cf1 100644 --- a/mywust-core/src/main/java/cn/linghang/mywust/core/api/UnionAuth.java +++ b/mywust-core/src/main/java/cn/linghang/mywust/core/api/UnionAuth.java @@ -5,4 +5,8 @@ public class UnionAuth { * 统一认证登录验证的api地址,请求之后可进一步获取service ticket来对具体的服务进行登录获取Cookies */ public static final String UNION_AUTH_API = "https://auth.wust.edu.cn/lyuapServer/v1/tickets"; + + public static final String LIBRARY_SSO_SERVICE = "https://libsys.wust.edu.cn:443/meta-local/opac/cas/rosetta"; + + public static final String BKJX_SSO_SERVICE = "http://bkjx.wust.edu.cn/jsxsd/sso.jsp"; } diff --git a/mywust-core/src/main/java/cn/linghang/mywust/core/service/auth/AuthRequestFactory.java b/mywust-core/src/main/java/cn/linghang/mywust/core/service/auth/AuthRequestFactory.java new file mode 100644 index 0000000..ad42c22 --- /dev/null +++ b/mywust-core/src/main/java/cn/linghang/mywust/core/service/auth/AuthRequestFactory.java @@ -0,0 +1,37 @@ +package cn.linghang.mywust.core.service.auth; + +import cn.linghang.mywust.network.HttpRequest; +import cn.linghang.mywust.util.StringUtil; + +import java.nio.charset.StandardCharsets; +import java.util.HashMap; +import java.util.Map; + +public class AuthRequestFactory { + public static HttpRequest unionLoginTGTRequest(String username, String password, String service) { + Map requestForm = new HashMap<>(4); + requestForm.put("username", username); + requestForm.put("password", password); + requestForm.put("service", service); + requestForm.put("loginType", ""); + + String queryString = StringUtil.generateQueryString(requestForm); + + HttpRequest request = new HttpRequest(); + request.setData(queryString.getBytes(StandardCharsets.UTF_8)); + + return request; + } + + public static HttpRequest loginTicketRequest(String service) { + Map requestForm = new HashMap<>(1); + requestForm.put("service", service); + + String queryString = StringUtil.generateQueryString(requestForm); + + HttpRequest request = new HttpRequest(); + request.setData(queryString.getBytes(StandardCharsets.UTF_8)); + + return request; + } +} diff --git a/mywust-core/src/main/java/cn/linghang/mywust/core/service/auth/UnionLogin.java b/mywust-core/src/main/java/cn/linghang/mywust/core/service/auth/UnionLogin.java index 2749917..a16fea3 100644 --- a/mywust-core/src/main/java/cn/linghang/mywust/core/service/auth/UnionLogin.java +++ b/mywust-core/src/main/java/cn/linghang/mywust/core/service/auth/UnionLogin.java @@ -3,7 +3,7 @@ package cn.linghang.mywust.core.service.auth; import cn.linghang.mywust.core.api.UnionAuth; import cn.linghang.mywust.core.exception.BasicException; import cn.linghang.mywust.core.exception.PasswordWornException; -import cn.linghang.mywust.core.service.undergraduate.AuthRequestFactory; +import cn.linghang.mywust.core.service.undergraduate.BkjxAuthRequestFactory; import cn.linghang.mywust.network.HttpRequest; import cn.linghang.mywust.network.HttpResponse; import cn.linghang.mywust.network.RequestClientOption; diff --git a/mywust-core/src/main/java/cn/linghang/mywust/core/service/library/LibraryAuthRequestFactory.java b/mywust-core/src/main/java/cn/linghang/mywust/core/service/library/LibraryAuthRequestFactory.java new file mode 100644 index 0000000..d2f25bc --- /dev/null +++ b/mywust-core/src/main/java/cn/linghang/mywust/core/service/library/LibraryAuthRequestFactory.java @@ -0,0 +1,14 @@ +package cn.linghang.mywust.core.service.library; + +import cn.linghang.mywust.network.HttpRequest; +import cn.linghang.mywust.network.RequestFactory; + +public class LibraryAuthRequestFactory extends RequestFactory { + public static HttpRequest sessionCookieRequest() { + return DEFAULT_HTTP_REQUEST; + } + + public static HttpRequest indexRequest() { + return DEFAULT_HTTP_REQUEST; + } +} diff --git a/mywust-core/src/main/java/cn/linghang/mywust/core/service/library/LibraryLogin.java b/mywust-core/src/main/java/cn/linghang/mywust/core/service/library/LibraryLogin.java new file mode 100644 index 0000000..98aeb82 --- /dev/null +++ b/mywust-core/src/main/java/cn/linghang/mywust/core/service/library/LibraryLogin.java @@ -0,0 +1,57 @@ +package cn.linghang.mywust.core.service.library; + +import cn.linghang.mywust.core.api.Bkjx; +import cn.linghang.mywust.core.api.Library; +import cn.linghang.mywust.core.api.UnionAuth; +import cn.linghang.mywust.core.exception.BasicException; +import cn.linghang.mywust.core.service.auth.UnionLogin; +import cn.linghang.mywust.core.service.undergraduate.BkjxAuthRequestFactory; +import cn.linghang.mywust.network.HttpRequest; +import cn.linghang.mywust.network.HttpResponse; +import cn.linghang.mywust.network.RequestClientOption; +import cn.linghang.mywust.network.Requester; + +import java.io.IOException; +import java.net.MalformedURLException; +import java.net.URL; + +public class LibraryLogin { + private final Requester requester; + + private final UnionLogin unionLogin; + + public LibraryLogin(Requester requester, UnionLogin unionLogin) { + this.requester = requester; + this.unionLogin = unionLogin; + } + + public String getLibraryLoginCookie(String username, String password, RequestClientOption requestOption) throws BasicException, IOException { + String serviceTicket = unionLogin.getServiceTicket(username, password, UnionAuth.LIBRARY_SSO_SERVICE, requestOption); + + // 获取登录cookie(session) + HttpRequest sessionRequest = LibraryAuthRequestFactory.sessionCookieRequest(); + HttpResponse sessionResponse = requester.get(new URL(String.format(Library.LIBRARY_SESSION_COOKIE_API, serviceTicket)), sessionRequest, requestOption); + String cookies = sessionResponse.getCookies(); + + // 请求一次首页 + HttpRequest indexRequest = LibraryAuthRequestFactory.indexRequest(); + indexRequest.setCookies(cookies); + requester.get(new URL(Library.LIBRARY_INDEX_URL), indexRequest, requestOption); + + return cookies; + } + + public boolean checkCookie(String cookies) throws IOException { + RequestClientOption option = RequestClientOption.DEFAULT_OPTION; + + HttpRequest testRequest = LibraryAuthRequestFactory.getDefaultHttpRequest(); + testRequest.setCookies(cookies); + HttpResponse testResponse = requester.get(new URL(Library.LIBRARY_COOKIE_TEST_URL), testRequest, option); + + // 响应居然是JSON,好评! + // 但是我们只要看有没有Unauthorized关键字就行了 + // 未认证的话是Unauthorized(如果人家没有抽风改掉的话) + byte[] responseData = testResponse.getBody(); + return responseData != null && !new String(responseData).equalsIgnoreCase("Unauthorized"); + } +} diff --git a/mywust-core/src/main/java/cn/linghang/mywust/core/service/undergraduate/AuthRequestFactory.java b/mywust-core/src/main/java/cn/linghang/mywust/core/service/undergraduate/BkjxAuthRequestFactory.java similarity index 54% rename from mywust-core/src/main/java/cn/linghang/mywust/core/service/undergraduate/AuthRequestFactory.java rename to mywust-core/src/main/java/cn/linghang/mywust/core/service/undergraduate/BkjxAuthRequestFactory.java index f69d909..5e56bbd 100644 --- a/mywust-core/src/main/java/cn/linghang/mywust/core/service/undergraduate/AuthRequestFactory.java +++ b/mywust-core/src/main/java/cn/linghang/mywust/core/service/undergraduate/BkjxAuthRequestFactory.java @@ -1,45 +1,21 @@ package cn.linghang.mywust.core.service.undergraduate; import cn.linghang.mywust.network.HttpRequest; +import cn.linghang.mywust.network.RequestFactory; import cn.linghang.mywust.util.StringUtil; import java.nio.charset.StandardCharsets; import java.util.HashMap; import java.util.Map; -public class AuthRequestFactory { - public static HttpRequest unionLoginTGTRequest(String username, String password, String service) { - Map requestForm = new HashMap<>(4); - requestForm.put("username", username); - requestForm.put("password", password); - requestForm.put("service", service); - requestForm.put("loginType", ""); - - String queryString = StringUtil.generateQueryString(requestForm); - - HttpRequest request = new HttpRequest(); - request.setData(queryString.getBytes(StandardCharsets.UTF_8)); - - return request; - } - - public static HttpRequest loginTicketRequest(String service) { - Map requestForm = new HashMap<>(1); - requestForm.put("service", service); - - String queryString = StringUtil.generateQueryString(requestForm); - - HttpRequest request = new HttpRequest(); - request.setData(queryString.getBytes(StandardCharsets.UTF_8)); - - return request; - } - +public class BkjxAuthRequestFactory extends RequestFactory { public static HttpRequest sessionCookieRequest() { return DEFAULT_HTTP_REQUEST; } - private static final HttpRequest DEFAULT_HTTP_REQUEST = new HttpRequest(); + public static HttpRequest getDefaultHttpRequest() { + return DEFAULT_HTTP_REQUEST; + } public static class Legacy { public static HttpRequest dataStringRequest() { diff --git a/mywust-core/src/main/java/cn/linghang/mywust/core/service/undergraduate/JwcLogin.java b/mywust-core/src/main/java/cn/linghang/mywust/core/service/undergraduate/JwcLogin.java index 97f4482..592a357 100644 --- a/mywust-core/src/main/java/cn/linghang/mywust/core/service/undergraduate/JwcLogin.java +++ b/mywust-core/src/main/java/cn/linghang/mywust/core/service/undergraduate/JwcLogin.java @@ -1,6 +1,7 @@ package cn.linghang.mywust.core.service.undergraduate; import cn.linghang.mywust.core.api.Bkjx; +import cn.linghang.mywust.core.api.UnionAuth; import cn.linghang.mywust.core.exception.BasicException; import cn.linghang.mywust.core.exception.PasswordWornException; import cn.linghang.mywust.core.service.auth.UnionLogin; @@ -28,15 +29,16 @@ public class JwcLogin { } /** - *

旧版的登录方式,既相当于直接登录bkjx系统

+ *

旧版的登录方式,既相当于直接登录bkjx系统,不建议使用

*

注意,这种登录方式的密码和新版可能是不一样的

*

不过不论使用哪种登录方式获取到的cookie都是可用的

* * @return 获取到的Cookies */ + @Deprecated public String getLoginCookieLegacy(String username, String password, RequestClientOption requestOption) throws IOException, BasicException { // 获取某段神秘的dataStr(反正官网代码是这么叫的) - HttpRequest dataStringRequest = AuthRequestFactory.Legacy.dataStringRequest(); + HttpRequest dataStringRequest = BkjxAuthRequestFactory.Legacy.dataStringRequest(); HttpResponse dataStringResponse = requester.post(new URL(Bkjx.Legacy.BKJX_DATA_STRING_API), dataStringRequest, requestOption); if (dataStringResponse.getBody() == null) { throw new BasicException(); @@ -46,7 +48,7 @@ public class JwcLogin { // 获取登录ticket String encoded = PasswordEncoder.legacyPassword(username, password, dataString); - HttpRequest ticketRequest = AuthRequestFactory.Legacy.ticketRedirectRequest(encoded); + HttpRequest ticketRequest = BkjxAuthRequestFactory.Legacy.ticketRedirectRequest(encoded); ticketRequest.setCookies(dataStringResponse.getCookies()); HttpResponse ticketResponse = requester.post(new URL(Bkjx.Legacy.BKJX_SESSION_COOKIE_API), ticketRequest, requestOption); if (ticketResponse.getBody() == null) { @@ -58,7 +60,7 @@ public class JwcLogin { if (sessionRedirect == null) { throw new PasswordWornException(); } - HttpRequest sessionRequest = AuthRequestFactory.Legacy.dataStringRequest(); + HttpRequest sessionRequest = BkjxAuthRequestFactory.Legacy.dataStringRequest(); HttpResponse sessionResponse = requester.get(new URL(sessionRedirect), sessionRequest, requestOption); @@ -71,10 +73,10 @@ public class JwcLogin { } public String getLoginCookie(String username, String password, RequestClientOption requestOption) throws IOException, BasicException { - String serviceTicket = unionLogin.getServiceTicket(username, password, Bkjx.BKJX_SSO_SERVICE, requestOption); + String serviceTicket = unionLogin.getServiceTicket(username, password, UnionAuth.BKJX_SSO_SERVICE, requestOption); // 获取登录cookie(session) - HttpRequest sessionRequest = AuthRequestFactory.sessionCookieRequest(); + HttpRequest sessionRequest = BkjxAuthRequestFactory.sessionCookieRequest(); HttpResponse sessionResponse = requester.get(new URL(String.format(Bkjx.BKJX_SESSION_COOKIE_API, serviceTicket)), sessionRequest, requestOption); String cookies = sessionResponse.getCookies(); @@ -96,12 +98,9 @@ public class JwcLogin { public boolean checkCookies(String cookies) throws IOException { - RequestClientOption option = new RequestClientOption(); - option.setTimeout(5); - option.setProxy(null); - option.setFallowUrlRedirect(false); + RequestClientOption option = RequestClientOption.DEFAULT_OPTION; - HttpRequest testRequest = AuthRequestFactory.sessionCookieRequest(); + HttpRequest testRequest = BkjxAuthRequestFactory.getDefaultHttpRequest(); testRequest.setCookies(cookies); HttpResponse testResponse = requester.get(new URL(Bkjx.BKJX_TEST_API), testRequest, option); diff --git a/mywust-network-okhttp/src/main/java/cn/linghang/mywust/network/okhttp/SimpleOkhttpRequester.java b/mywust-network-okhttp/src/main/java/cn/linghang/mywust/network/okhttp/SimpleOkhttpRequester.java index e5f14b2..5d03110 100644 --- a/mywust-network-okhttp/src/main/java/cn/linghang/mywust/network/okhttp/SimpleOkhttpRequester.java +++ b/mywust-network-okhttp/src/main/java/cn/linghang/mywust/network/okhttp/SimpleOkhttpRequester.java @@ -15,6 +15,7 @@ import java.net.InetSocketAddress; import java.net.Proxy; import java.net.URL; import java.nio.charset.StandardCharsets; +import java.util.Arrays; import java.util.List; import java.util.Map; import java.util.TreeMap; @@ -256,6 +257,9 @@ public class SimpleOkhttpRequester implements Requester { List cookieHeaders = response.headers("Set-Cookie"); httpResponse.setCookies(StringUtil.parseCookie(cookieHeaders)); + log.debug("Receive Response: {}", response); + log.debug("Response Headers: {}", responseHeaders); +// log.debug("Response body: {}", new String(Arrays.copyOf(httpResponse.getBody(), 64))); return httpResponse; } } @@ -274,6 +278,11 @@ public class SimpleOkhttpRequester implements Requester { OkHttpClient client = getOkhttpClient(requestClientOption); Request request = this.buildRequest(requestMethod, url, httpRequest); + log.debug("------------Do Request------------"); + log.debug("Request Options: {}" ,requestClientOption); + log.debug("Request: {}", request); + log.debug("Headers: {}", request.headers()); + return this.sendRequest(client, request); } diff --git a/mywust-network/src/main/java/cn/linghang/mywust/network/RequestClientOption.java b/mywust-network/src/main/java/cn/linghang/mywust/network/RequestClientOption.java index 07454b3..de480bf 100644 --- a/mywust-network/src/main/java/cn/linghang/mywust/network/RequestClientOption.java +++ b/mywust-network/src/main/java/cn/linghang/mywust/network/RequestClientOption.java @@ -13,4 +13,15 @@ public class RequestClientOption { private String address; private int port; } + + public static final RequestClientOption DEFAULT_OPTION = newDefaultOption(); + + private static RequestClientOption newDefaultOption() { + RequestClientOption option = new RequestClientOption(); + option.setTimeout(5); + option.setProxy(null); + option.setFallowUrlRedirect(false); + + return option; + } } diff --git a/mywust-network/src/main/java/cn/linghang/mywust/network/RequestFactory.java b/mywust-network/src/main/java/cn/linghang/mywust/network/RequestFactory.java new file mode 100644 index 0000000..18a71b4 --- /dev/null +++ b/mywust-network/src/main/java/cn/linghang/mywust/network/RequestFactory.java @@ -0,0 +1,9 @@ +package cn.linghang.mywust.network; + +public class RequestFactory { + protected static final HttpRequest DEFAULT_HTTP_REQUEST = new HttpRequest(); + + public static HttpRequest getDefaultHttpRequest() { + return DEFAULT_HTTP_REQUEST; + } +} diff --git a/mywust-test/pom.xml b/mywust-test/pom.xml index 166ac2e..2773ef3 100644 --- a/mywust-test/pom.xml +++ b/mywust-test/pom.xml @@ -20,6 +20,17 @@ 1.0-SNAPSHOT test + + + ch.qos.logback + logback-classic + 1.2.11 + + + ch.qos.logback + logback-core + 1.2.11 + diff --git a/mywust-test/src/test/java/JwcLegacyLoginTest.java b/mywust-test/src/test/java/JwcLegacyLoginTest.java index ddf3af6..bd8c0e3 100644 --- a/mywust-test/src/test/java/JwcLegacyLoginTest.java +++ b/mywust-test/src/test/java/JwcLegacyLoginTest.java @@ -14,6 +14,7 @@ public class JwcLegacyLoginTest { } private void run() throws BasicException, IOException { + System.out.println("bkjx旧版直登测试"); System.out.println("输入账号(学号)和密码,用“ ”(空格)分割"); Scanner scanner = new Scanner(System.in); diff --git a/mywust-test/src/test/java/JwcLoginTest.java b/mywust-test/src/test/java/JwcLoginTest.java index 552ff17..0a8f5c8 100644 --- a/mywust-test/src/test/java/JwcLoginTest.java +++ b/mywust-test/src/test/java/JwcLoginTest.java @@ -14,6 +14,7 @@ public class JwcLoginTest { } private void run() throws BasicException, IOException { + System.out.println("bkjx登录测试(统一身份验证)"); System.out.println("输入账号(学号)和密码,用“ ”(空格)分割"); Scanner scanner = new Scanner(System.in); @@ -36,6 +37,8 @@ public class JwcLoginTest { String cookies = jwcLogin.getLoginCookie(username, password, option); - System.out.println(cookies); + System.out.printf("获取到Cookies: %s \n", cookies); + + System.out.printf("检查Cookies: %s", jwcLogin.checkCookies(cookies)); } } diff --git a/mywust-test/src/test/java/LibraryLoginTest.java b/mywust-test/src/test/java/LibraryLoginTest.java new file mode 100644 index 0000000..9c0530e --- /dev/null +++ b/mywust-test/src/test/java/LibraryLoginTest.java @@ -0,0 +1,42 @@ +import cn.linghang.mywust.core.exception.BasicException; +import cn.linghang.mywust.core.service.auth.UnionLogin; +import cn.linghang.mywust.core.service.library.LibraryLogin; +import cn.linghang.mywust.core.service.undergraduate.JwcLogin; +import cn.linghang.mywust.network.RequestClientOption; +import cn.linghang.mywust.network.Requester; +import cn.linghang.mywust.network.okhttp.SimpleOkhttpRequester; + +import java.io.IOException; +import java.util.Scanner; + +public class LibraryLoginTest { + public static void main(String[] args) throws BasicException, IOException { + new LibraryLoginTest().run(); + } + + private void run() throws BasicException, IOException { + System.out.println("图书馆登陆测试"); + System.out.println("输入账号(学号)和密码,用“ ”(空格)分割"); + + Scanner scanner = new Scanner(System.in); + + String input = scanner.nextLine(); + + String username = input.split(" ")[0]; + String password = input.split(" ")[1]; + + System.out.println("账号:" + username); + System.out.println("密码:" + password); + + Requester requester = new SimpleOkhttpRequester(); + LibraryLogin libraryLogin = new LibraryLogin(requester, new UnionLogin(requester)); + + RequestClientOption option = RequestClientOption.DEFAULT_OPTION; + + String cookies = libraryLogin.getLibraryLoginCookie(username, password, option); + + System.out.printf("获取到的cookies: %s \n", cookies); + + System.out.printf("检查Cookies: %s", libraryLogin.checkCookie(cookies)); + } +}