实现QQ、微信、新浪微博和百度第三方登录(Android Studio)

前言:
对于大多数的APP都有第三方登录这个功能,自己也做过几次,最近又有一个新项目用到了第三方登录,所以特意总结了一下关于第三方登录的实现,并拿出来与大家一同分享;

各大开放平台注册账户获取AppKey和AppSecret
Mob开放平台地址:http://www.mob.com/#/index
QQ开放平台地址:http://open.qq.com/
新浪微博开放平台地址:http://open.weibo.com/
微信开放平台地址:https://open.weixin.qq.com/
百度开放平台地址:http://apps.bdimg.com/

注:
一、关于各大开放平台的开发者用户注册和创建应用获取AppKey、AppSecret我就不多说了,对于大家来说这都so easy;
二、Eclipse在创建应用填写包名应该是manifest里面的packpage:

studio的则是build.gradle里面的applicationId

一般情况下,studioapplicationIdmanifest下的包名是一致的,但是applicationId是手动改变的,所以注意在创建应用的时候,要使用applicationId

新浪微博第三方登录实现:

在做新浪微博第三方登录的时候,参考他们的api文档,感觉他们的api文档写的特别的乱,并且下载的Demo运行还报错,以至于浪费了我大半天的时间,去网上搜了几篇关于第三方登录的文章,写的并不全,时代也比较久远,并且基本没有相关Demo下载,有的就是拷贝的新浪微博的开放平台的原文,我也是醉了…..
由于时间比较紧迫,所以并没有再继续深究下去。大家应该都知道有许多平台把例如分享、登录等功能集成好了,实现功能十分简单,这一次我是利用的Mob移动开发平台http://www.mob.com/#/index 实现的新浪微博第三方登录,感觉还不错实现起来比较简单。

一、下载Mob平台的SDK
首先下载SDK,得到我们需要的资源

SDK地址(http://www.mob.com/#/downloadDetail/ShareSDK/android),下载下来发现无法解压(你们可以试一下),联系他们客服,他们说:上传错误,就给我发了一个。我把它和我的Dmeo放在一起,可供下载。
找到ShareSDK for Android包下的QuickIntegrater.jar文件双击:

感觉还不错,各大平台都有,只需要选择新浪微博就可以(我感觉还是没包装过的比较好,所以另外三种登录方式没采用这种方法),解压之后生成一个Sample文件:

我们需要把里面的东西全部拿到我们的studio项目中,libs、res和src里面的全部拷贝复制就可以,studio新建assets的方法和Eclipse不一样,所以给大家发个图:

点击创建就可以了,再把assets下的ShareSDK.xml拷贝就去;

其次配置ShareSDK
把ShareSDK拷贝进去之后,我们需要把ShareSDK.xml文件中关于Mob(ShareSDK)和新浪微博(SinaWeibo)的Appkey、AppSecret和RedirectUrl替换成我们申请的值,如下图:

把红箭头中的ShareSDK中的AppKey换成我们在Mob后台申请的AppKey;
红框框中的SinaWeibo中的AppKey、AppSecret和RedirectUrl换成我们在新浪微博后台申请的对应的值;
RedirectUrl这个字段的值就是我们后台项目中的应用信息——>高级信息——>OAuth2.0 授权设置中的授权回调页这个字段,需要我们填写一个有效的地址就可以,例如下图:


注:如果RedirectUrl这个字段不填或填写不对会报以下错误:

二、配置AndroidManifest.xml
添加activity信息

<activity
android:name="com.mob.tools.MobUIShell"
android:theme="@android:style/Theme.Translucent.NoTitleBar"
android:configChanges="keyboardHidden|orientation|screenSize"
android:screenOrientation="portrait"
android:windowSoftInputMode="stateHidden|adjustResize" >
</activity>

二、添加代码
首先是Mob的授权,在程序的入口处添加授权代码:

//Mob平台授权
ShareSDK.initSDK(this);

其次直接调用thirdSinaLogin()方法就可以了:

//-----------------------------------------------------新浪微博授权相关--------------
/** 新浪微博授权、获取用户信息页面 */
private void thirdSinaLogin() {
//初始化新浪平台
Platform pf = ShareSDK.getPlatform(MainActivity.this, SinaWeibo.NAME);
pf.SSOSetting(true);
//设置监听
pf.setPlatformActionListener(MainActivity.this);
//获取登陆用户的信息,如果没有授权,会先授权,然后获取用户信息
pf.authorize();
}
/** 新浪微博授权成功回调页面 */
@Override
public void onComplete(Platform platform, int action, HashMap<String, Object> hashMap) {
/** res是返回的数据,例如showUser(null),返回用户信息,对其解析就行
* http://sharesdk.cn/androidDoc/cn/sharesdk/framework/PlatformActionListener.html
*
*/
Message msg = new Message();
msg.what = MSG_ACTION_CCALLBACK;
msg.arg1 = 1;
msg.arg2 = action;
msg.obj = platform;
UIHandler.sendMessage(msg, this);
}
/** 取消授权 */
@Override
public void onCancel(Platform platform, int action) {
Message msg = new Message();
msg.what = MSG_ACTION_CCALLBACK;
msg.arg1 = 3;
msg.arg2 = action;
msg.obj = platform;
UIHandler.sendMessage(msg, this);
}
/** 授权失败 */
@Override
public void onError(Platform platform, int action, Throwable t) {
t.printStackTrace();
t.getMessage();
Message msg = new Message();
msg.what = MSG_ACTION_CCALLBACK;
msg.arg1 = 2;
msg.arg2 = action;
msg.obj = t;
UIHandler.sendMessage(msg, this);
} @Override
public boolean handleMessage(Message msg) {
switch(msg.what) {
case MSG_TOAST: {
String text = String.valueOf(msg.obj);
Toast.makeText(MainActivity.this, text, Toast.LENGTH_SHORT).show();
}
break;
case MSG_ACTION_CCALLBACK: {
switch (msg.arg1) {
case 1: {
// 成功, successful notification
//授权成功后,获取用户信息,要自己解析,看看oncomplete里面的注释
//ShareSDK只保存以下这几个通用值
Platform pf = ShareSDK.getPlatform(MainActivity.this, SinaWeibo.NAME);
Log.e("sharesdk use_id", pf.getDb().getUserId()); //获取用户id
Log.e("sharesdk use_name", pf.getDb().getUserName());//获取用户名称
Log.e("sharesdk use_icon", pf.getDb().getUserIcon());//获取用户头像
mThirdLoginResult.setText("授权成功"+"\n"+"用户id:" + pf.getDb().getUserId() + "\n" + "获取用户名称" + pf.getDb().getUserName() + "\n" + "获取用户头像" + pf.getDb().getUserIcon());
//mPf.author()这个方法每一次都会调用授权,出现授权界面
//如果要删除授权信息,重新授权
//mPf.getDb().removeAccount();
//调用后,用户就得重新授权,否则下一次就不用授权
}
break;
case 2: {
mThirdLoginResult.setText("登录失败");
}
break;
case 3: {
// 取消, cancel notification
mThirdLoginResult.setText("取消授权");
}
break;
}
}
break;
case MSG_CANCEL_NOTIFY: {
NotificationManager nm = (NotificationManager) msg.obj;
if (nm != null) {
nm.cancel(msg.arg1);
}
}
break;
}
return false;
}

最后退出登录

    Platform mPf = ShareSDK.getPlatform(MainActivity.this, SinaWeibo.NAME);
//如果要删除授权信息,重新授权
ShareSDK.removeCookieOnAuthorize(true);
mPf.removeAccount();

到这里关于新浪微博第三方登录的就基本结束了,我们获取到了用户的id、昵称、头像地址等信息,使用唯一值id再结合自己服务器的接口,便可实现第三方登录了.效果图如下:


注意:如果你想修改授权的登录页面,可以参考
这个链接里面的第11条

QQ第三方登录实现:

注意
一、我不建议大家去看QQ开放平台关于获取个人信息那部分的文档,因为他们的文档已经过时了,我当时按照文档做过,但是一直报错,后来问客服,他告诉我他们的文档它久远了,已经不能用了<当时我就醉了、、>,而是给了我一份Demo,我会把Demo放在里面供大家下载。
二、大家使用的测试机一定要是自动获取的网络时间,否则得不到信息,并且也没有错误信息,我研究了半天的时间,也没找到到底为什么,一问客服才知道,服务器时间和请求时间戳要相同才可以<我又是醉了、、、>。
三、大家要打包APP再进行测试。

QQ第三方登录的步骤分为:
1.先登录成功获取token和openid
2.再通过token和openid获取用户的信息。

一、导入SDK的jar文件
把这两个jar文件导入项目中

二、配置AndroidManifest

<!-- QQ第三方登录相关       开始 -->
<activity
android:name="com.tencent.tauth.AuthActivity"
android:launchMode="singleTask"
android:noHistory="true" >
<intent-filter>
<action android:name="android.intent.action.VIEW" /> <category android:name="android.intent.category.DEFAULT" />
<category android:name="android.intent.category.BROWSABLE" /> <data android:scheme="tencent你的APPId" />
</intent-filter>
</activity>
<activity android:name="com.tencent.connect.common.AssistActivity"
android:theme="@android:style/Theme.Translucent.NoTitleBar"
android:configChanges="orientation|keyboardHidden|screenSize"
/>
<!-- QQ第三方登录相关 结束 -->

scheme这个字段输入你申请的appid,tencent不要删掉。

三、添加代码
首先在程序入口添加:

Tencent mTencent = Tencent.createInstance(你的AppId, this.getApplicationContext());

剩下的调用loginQQ方法便可以:

/** ------------------------QQ第三方登录-------------------- */
public void loginQQ(){
/** 判断是否登陆过 */
if (!mTencent.isSessionValid()){
mTencent.login(this, "all",loginListener);
}/** 登陆过注销之后在登录 */
else {
mTencent.logout(this);
mTencent.login(this, "all",loginListener);
}
}
IUiListener loginListener = new BaseUiListener() {
@Override
protected void doComplete(JSONObject values) {
initOpenidAndToken(values);
updateUserInfo();
}
};
/** QQ登录第二步:存储token和openid */
public static void initOpenidAndToken(JSONObject jsonObject) {
try {
String token = jsonObject.getString(Constants.PARAM_ACCESS_TOKEN);
String expires = jsonObject.getString(Constants.PARAM_EXPIRES_IN);
String openId = jsonObject.getString(Constants.PARAM_OPEN_ID);
if (!TextUtils.isEmpty(token) && !TextUtils.isEmpty(expires) && !TextUtils.isEmpty(openId)) {
mTencent.setAccessToken(token, expires);
mTencent.setOpenId(openId);
}
} catch(Exception e) {
}
}
/** QQ登录第三步:获取用户信息 */
private void updateUserInfo() {
if (mTencent != null && mTencent.isSessionValid()) {
IUiListener listener = new IUiListener() {
@Override
public void onError(UiError e) {
Message msg = new Message();
msg.obj = "把手机时间改成获取网络时间";
msg.what = 1;
mHandler.sendMessage(msg);
} @Override
public void onComplete(final Object response) {
Message msg = new Message();
msg.obj = response;
msg.what = 0;
mHandler.sendMessage(msg);
}
@Override
public void onCancel() {
Message msg = new Message();
msg.obj = "获取用户信息失败";
msg.what = 2;
mHandler.sendMessage(msg);
}
};
mInfo = new UserInfo(this, mTencent.getQQToken());
mInfo.getUserInfo(listener);
} else { }
}
Handler mHandler = new Handler() {
@Override
public void handleMessage(Message msg) {
/** 获取用户信息成功 */
if (msg.what == 0) {
JSONObject response = (JSONObject) msg.obj;
if (response.has("nickname")) {
try {
log("获取用户信息成功,返回结果:"+response.toString());
mThirdLoginResult.setText("登录成功\n"+"用户id:"+openid+"\n昵称:"+response.getString("nickname")+"\n头像地址:"+response.get("figureurl_qq_1"));
} catch (JSONException e) {
e.printStackTrace();
}
}
}else if(msg.what == 1){
mThirdLoginResult.setText(msg+"");
}else if(msg.what == 2){
mThirdLoginResult.setText(msg+"");
}
} };
/** QQ登录第一步:获取token和openid */
private class BaseUiListener implements IUiListener {
@Override
public void onComplete(Object response) {
if (null == response) {
mToast("登录失败");
return;
}
JSONObject jsonResponse = (JSONObject) response;
if (null != jsonResponse && jsonResponse.length() == 0) {
mToast("登录失败");
return;
}
log("QQ登录成功返回结果-" + response.toString());
doComplete((JSONObject)response);
}
protected void doComplete(JSONObject response) {}
@Override
public void onError(UiError e) {
Util.toastMessage(MainActivity.this, "onError: " + e.errorDetail);
Util.dismissDialog();
}
@Override
public void onCancel() {
Util.toastMessage(MainActivity.this, "onCancel: ");
Util.dismissDialog();
if (isServerSideLogin) {
isServerSideLogin = false;
}
}
}
/** -------------------------QQ第三方登录结束-------------------- */

代码有注释,大家看一下应该很容易明白。

QQ可以获得以下相关信息:
大家只要response.getString(“字段名”)就可以得到数据了:

{
"is_yellow_year_vip": "0",
"ret": 0,
"figureurl_qq_1": "http://q.qlogo.cn/qqapp/222222/8C75BBE3DC6B0E9A64BD31449A3C8CB0/40",
"figureurl_qq_2": "http://q.qlogo.cn/qqapp/222222/8C75BBE3DC6B0E9A64BD31449A3C8CB0/100",
"nickname": "小罗",
"yellow_vip_level": "0",
"msg": "",
"figureurl_1": "http://qzapp.qlogo.cn/qzapp/222222/8C75BBE3DC6B0E9A64BD31449A3C8CB0/50",
"vip": "0",
"level": "0",
"figureurl_2": "http://qzapp.qlogo.cn/qzapp/222222/8C75BBE3DC6B0E9A64BD31449A3C8CB0/100",
"is_yellow_vip": "0",
"gender": "男",
"figureurl": "http://qzapp.qlogo.cn/qzapp/222222/8C75BBE3DC6B0E9A64BD31449A3C8CB0/30"
}

最后退出登录:

mTencent.logout(this);

给大家看一下截图:

微信第三方登录
微信平台还是做得挺不错的,大家可以看一下他们的文档,只不过我们需要自己写网络请求(衰衰衰衰衰)

微信第三方登录分为:
1.获取code
2.根据code获取token
3.根据token获取用户信息
在第二、三步需要我们自己去写网络请求,我也是醉了。。。。

一、导入SDK的libammsdk.jar文件,我就不多说了
二、配置AndroidManifest
在你的build.gradle的applicationId相应目录下新建一个wxapi目录,在该wxapi目录下新增一个WXEntryActivity类,该类继承自Activity(例如应用程序build.gradle的applicationId为com.aohuan.jinghai_lifee,则新添加的类如下图所示)

并在manifest文件里面加上exported属性,设置为true,例如:

<activity
android:name="com.aohuan.jinghai_lifee.wxapi.WXEntryActivity"
android:exported="true"
android:label="@string/app_name" >
</activity>

三、添加代码

/** -------------------------微信第三方登录---------------------- */
/**
*
* 微信平台应用授权登录接入代码示例
*
* */
private void regToWx(){
// 通过WXAPIFactory工厂,获得IWXAPI的实例
api = WXAPIFactory.createWXAPI(MainActivity.this, AllApk.WEIXIN_APP_ID, true);
// 将应用的appid注册到微信
api.registerApp(AllApk.WEIXIN_APP_ID);
}
//获取微信访问getCode
private void getCode(){
final SendAuth.Req req = new SendAuth.Req();
req.scope = "snsapi_userinfo";
req.state = "carjob_wx_login";
api.sendReq(req);
}
/** -------------------------微信第三方登录结束-------------------- */

首先在onCreate()方法里面调用regToWx()方法实现微信平台的注册;
其次第一步获取code
调用getCode()方法发送获取code的请求,接受code则是在WXEntryActivity这个类里面的onResp():

第二步使用AsyncTask获取token:

/** 微信登录第二步:获取token */
class AsynctaskToken extends AsyncTask<Object , Object , Object> {
@Override
protected Object doInBackground(Object... params) {
HttpGet httpRequest = new HttpGet(params[0].toString());
try{
HttpClient httpClient = new DefaultHttpClient();
HttpResponse httpResponse = httpClient.execute(httpRequest);
if(httpResponse.getStatusLine().getStatusCode() == HttpStatus.SC_OK){
BaseActivity.log("请求个人信息成功");
String strResult = EntityUtils.toString(httpResponse.getEntity());
return strResult;
}
else{
BaseActivity.log("请求个人信息失败");
return "请求出错";
}
}
catch(ClientProtocolException e){
}
catch (IOException e) {
e.printStackTrace();
}
return null;
} @Override
protected void onCancelled() {
super.onCancelled();
}
@Override
protected void onPostExecute(Object o) {
super.onPostExecute(o);
Object obj = null;
try {
obj = JsonUtil.toObjectByJson(o.toString(), WeiXinLoginGetTokenBean.class);
} catch (IOException e) {
e.printStackTrace();
}
WeiXinLoginGetTokenBean bean = (WeiXinLoginGetTokenBean)obj;
BaseActivity.log("获取token成功:\n" + "token:"+bean.getAccess_token()+"\nopenid"+bean.getOpenid());
String url = "https://api.weixin.qq.com/sns/userinfo?"+"access_token="+bean.getAccess_token()+"&openid="+bean.getOpenid();
new AsynctaskInfo().execute(url);
}
@Override
protected void onProgressUpdate(Object... values) {
super.onProgressUpdate(values);
}
}

第三步获取用户信息:

/** 微信登录第三步:获取用户信息 */
class AsynctaskInfo extends AsyncTask<Object , Object , Object> {
@Override
protected Object doInBackground(Object... params) {
HttpGet httpRequest = new HttpGet(params[0].toString());
try{
HttpClient httpClient = new DefaultHttpClient();
HttpResponse httpResponse = httpClient.execute(httpRequest);
if(httpResponse.getStatusLine().getStatusCode() == HttpStatus.SC_OK){
BaseActivity.log("请求个人信息成功");
String strResult = EntityUtils.toString(httpResponse.getEntity());
return strResult;
}
else{
BaseActivity.log("请求个人信息失败");
return "请求出错";
}
}
catch(ClientProtocolException e){
}
catch (IOException e) {
e.printStackTrace();
}
return null;
} @Override
protected void onCancelled() {
super.onCancelled();
}
@Override
protected void onPostExecute(Object o) {
super.onPostExecute(o);
Object obj = null;
try {
obj = JsonUtil.toObjectByJson(o.toString(), WeiXinLoginGetUserinfoBean.class);
} catch (IOException e) {
e.printStackTrace();
}
WeiXinLoginGetUserinfoBean bean = (WeiXinLoginGetUserinfoBean)obj;
BaseActivity.log("获取用户信息成功:\n" + "昵称:"+bean.getNickname()+"\n头像路径"+bean.getHeadimgurl());
Toast.makeText(mContext,"获取用户信息成功:\n"+"昵称:"+bean.getNickname() + "\n头像路径:"+bean.getHeadimgurl(),Toast.LENGTH_LONG).show();
finish();
}
@Override
protected void onProgressUpdate(Object... values) {
super.onProgressUpdate(values);
}
}

微信第三方登录就结束了,相对来说不算太复杂:

注:测试微信登录的时候,也需要打包测试,否则得不到数据;

百度第三方登录
百度第三方登录,相对来说就比较简单了

第一步:导入Baidu-Frontia-Full-Debug-2.0.6.jar包

第二步:配置AndroidManifest.xml

添加android:name=”com.baidu.frontia.ForntiaApplication”

第三步:添加代码
在程序入口初始化Fronta”

Frontia.init(this.getApplicationContext(),你的AppKey);

注册百度:

//注册百度
FrontiaAuthorization mAuthorization = Frontia.getAuthorization();

主要代码直接调用baiduLogin()方法就可以:

/**
* 百度第三方登录相关
*/
protected void baiduLogin() {
ArrayList<String> scope = new ArrayList<String>();
scope.add(Scope_Basic);
scope.add(Scope_Netdisk);
mAuthorization.authorize(this, FrontiaAuthorization.MediaType.BAIDU.toString(), scope, new FrontiaAuthorizationListener.AuthorizationListener() {
@Override
public void onSuccess(FrontiaUser result) {
if (null != mThirdLoginResult) {
mThirdLoginResult.setText("social id: " + result.getId() + "\n" + "token: " + result.getAccessToken() + "\n" + "expired: " + result.getExpiresIn());
}
}
@Override
public void onFailure(int errCode, String errMsg) {
if (null != mThirdLoginResult) {
mThirdLoginResult.setText("errCode:" + errCode + ", errMsg:" + errMsg);
}
}
@Override
public void onCancel() {
if (null != mThirdLoginResult) {
mThirdLoginResult.setText("cancel");
}
}
});
}

退出登录调用baiduExit()方法就可以:

/**
* 百度第三方退出相关
*/
protected void baiduExit() {
boolean result = mAuthorization.clearAuthorizationInfo(FrontiaAuthorization.MediaType.BAIDU.toString());
if (result) {
mThirdLoginResult.setText("百度退出成功");
} else {
mThirdLoginResult.setText("百度退出失败");
}
}

百度登录,挺简单的吧

1.四种登录方式已经整理好了,如果有什么地方写错了或者漏掉的,请查看我的Demo或者提出来。
2.由于这是第一次写博客,所以肯定有写的不好的地方,大家有什么意见可以提出来,相互交流沟通,共同进步。
3.由于我的源代码里面涉及到客户的信息,所以AppKey、AppSecret等信息,被我删掉了,如果想看我的Demo效果,需要修改小部分我的代码:
第一:把我com.aohuan.jinghai_lifee.wxapi换成你的applicationId(对应的包名).wxapi

第二:修改ShareSDK.xml里面对应的信息:

第三:修改manifest.xml里面对应的信息:

第四:修改AllApk里面对应的信息:

这样就可以了!!!

源码下载地址
GitHub下载地址:
https://github.com/fengmaolian/LoginAndShare

好累,下班回家(哈哈)

android第三方登陆的更多相关文章

  1. Android第三方登陆之新浪微博Weibo篇(原生登陆授权)

    前言 Android第三方登录可以说是非常的常见,今天主要先说一下新浪微博第三方登陆授权. SDK版本支持 SDK v3.0已经发布了支持iPhone和Android的版本. 须将你的应用的包名签名信 ...

  2. Android 中实现分享和第三方登陆---以新浪微博为例

    第三方登陆和分享功能在目前大部分APP中都有,分享功能可以将自己觉得有意义的东西分享给身边的朋友,而第三方登陆可以借助已经有巨大用户基础的平台(如QQ和新浪微博)的账号,让用户在使用自己APP的时候不 ...

  3. Android 第三方开源库收集整理(转)

    原文地址:http://blog.csdn.net/caoyouxing/article/details/42418591 Android开源库 自己一直很喜欢Android开发,就如博客签名一样,  ...

  4. 45.Android 第三方开源库收集整理(转)

    原文地址:http://blog.csdn.net/caoyouxing/article/details/42418591 Android开源库 自己一直很喜欢Android开发,就如博客签名一样,  ...

  5. QQ,微信第三方登陆

    感觉越是大公司的SDK越不好用,其实我也是一直在想为什么他们拿那么高的工资却干着不相应的事儿. 下面说下QQ和微信第三方登陆的一点坑 首先 (QQ互联)自带的sdk中  一个文件工程没有调用产生关联错 ...

  6. 网站添加第三方登陆(PHP版)

    这两周正在写毕业设计,我做的是一个问答网站.先介绍一下这个网站:这是一个关于大学生在线问答的网站,类似知乎和百度知道,不过功能没有人家多,毕竟这个网站我一个人在做.网站部署在阿里云,网站包括API,W ...

  7. OAuth协议——PHP第三方登陆协议

    慕课网Badguy老师的良心课程! 总会有那种什么都不想干的时候,但现在的日子又不这么允许个人的放纵,我一般就只有这几个选择:看课程视频,看书,看小说..好像还是有可以做的事情.其中,看课程视频有点无 ...

  8. 微信第三方登陆,无需注册一键登录,获取用户信息,PHP实现方法

    今天讲讲利用微信oauth2实现第三方登陆的实现方法. 先说说前提吧! 首先你得是服务号,并且是经过认证的.这样微信会给你很多第三方接口的权限,如果是订阅号或者没有认证的服务号那就不用想了! 一开始你 ...

  9. Android第三方开源对话消息提示框:SweetAlertDialog(sweet-alert-dialog)

    Android第三方开源对话消息提示框:SweetAlertDialog(sweet-alert-dialog) Android第三方开源对话消息提示框:SweetAlertDialog(sweet- ...

随机推荐

  1. 熟悉Eclipse开发工具

    一.熟悉Eclipse 1.Eclipse是由IBM公司投资4000万美元开发的集成开发工具.它基于Java语言编写,并且是开放源代码的.可扩展的,也是目前最流行的Java集成开发工具之一.另外,IB ...

  2. hive中导入json格式的数据(hive分区表)

    hive中建立外部分区表,外部数据格式是json的如何导入呢? json格式的数据表不必含有分区字段,只需要在hdfs目录结构中体现出分区就可以了 This is all according to t ...

  3. OpenERP在哪储存附件?

    我们知道对OpenERP中的每个内部对象(比如:业务伙伴,采购订单,销售订单,发货单,等等)我们都可以添加任意的附件,如图片,文档,视频等.那么这些附件在OpenERP内部是如何管理的呢? 默认情况下 ...

  4. 获取客户端真实ip

    // 获取客户端真实ip() protected function getIP() { global $ip; if (getenv("HTTP_CLIENT_IP")) $ip ...

  5. HTTP协议 (五) 代理

    HTTP协议 (五) 代理 阅读目录 什么是代理服务器 Fiddler就是个典型的代理 代理作用一:FQ 代理作用二:匿名访问 代理作用三:通过代理上网 代理作用四:通过代理缓存,加快上网速度 代理作 ...

  6. ceph命令

    chen@admin-node:~$ ceph --help General usage: ============== usage: ceph [-h] [-c CEPHCONF] [-i INPU ...

  7. Codeforces Round #376 (Div. 2) C D F

    在十五楼做的cf..一会一断...比赛的时候做出了ABCF 就没有时间了 之后没看题解写出了D..E是个神奇的博弈(递推或者dp?)看了题解也没有理解..先写了CDF.. C 有n个袜子 每个袜子都有 ...

  8. ThinkPHP3.2.3 的异常和错误屏蔽处理

    一.入口文件关闭调试,配置文件配置异常页面 在生产环境中系统的错误信息不能暴露给用户,入口文件的 APP_DEBUG 默认为开启状态 define('APP_DEBUG',true); 此时如果用户访 ...

  9. How to prevent SQL injection attacks?

    In our earlier tutorial on SQL Injection, one way to have prevented the SQL injection attack was by ...

  10. 改变UIButton 图片和文字的位置

    //设置字体和图片之间的间距 _btnLeft.titleEdgeInsets = UIEdgeInsetsMake(0, -_btnLeft.imageView.frame.size.width, ...