首页 文章 精选 留言 我的

精选列表

搜索[SSH客户端],共10000篇文章
优秀的个人博客,低调大师

okhttps v2.4.5 已经发布,轻量级 HTTP 客户端

okhttps v2.4.5 已经发布 此版本更新内容包括: 1、Websocket 新增 status() 方法 2、WebSocketTask 新增 isConnected() 方法,可判断连接是否已建立 3、抽象 DataSet(只读数据集)接口,Mapper 和 Array 为其子接 4、优化文件下载控制部分代码 因上版发布比较仓促,建议 v2.4.4 都升级到 v2.4.5 详情查看:https://gitee.com/ejlchina-zhxu/okhttps/releases/v2.4.5

优秀的个人博客,低调大师

gout v0.1.2 发布,Golang 实现的 http 客户端

项目地址 https://gitee.com/guonaihong/gout https://github.com/guonaihong/gout changlog #241上传进度(在v0.0.4版本中间件里面实现https://github.com/antlabs/gout-middleware) #248调整FormFile和FormType的优先级 #250新增关闭301中间件 上传进度条 currBytes是已经上传数据,totalBytes是数据总大小. currBytes/totalBytes就是上传进度百分比 package main import ( "bytes" "github.com/antlabs/gout-middleware/request" "github.com/guonaihong/gout" ) func main() { gout.POST(":8080").RequestUse(request.ProgressBar(func(currBytes, totalBytes int) { fmt.Printf("%d:%d-->%f%%\n", currBytes, totalBytes, float64(currBytes)/float64(totalBytes)) })).SetBody(strings.Repeat("1", 100000) /*这里构造大点的测试数据,使用时换成真实业务数据,就可以看到效果*/).Do() }

优秀的个人博客,低调大师

gout v0.1.0 发布,golang 实现的 http 客户端

项目地址 https://gitee.com/guonaihong/gout https://github.com/guonaihong/gout changlog #226bench:设置Rate(压测频率),Number和Duration会有误差(pr:#227) #231明确SetBody, BindBody传递nil指针返回错误(pr:#232) #235请求中间件设计(pr:#236) #234新增gzip压缩请求body功能 #233打开debug模式,http.Header数据里面有%号效果优化(pr:#239) 重要特性(加入请求中间件设计) 请求中间件地址 https://github.com/antlabs/gout-middleware 请求中间件example 请求body使用gzip压缩 import ( "github.com/antlabs/gout-middleware/request" "github.com/guonaihong/gout" ) func main() { gout.POST(":6666/compress"). RequestUse(request.GzipCompress()). SetBody("hello world"). Do() }

优秀的个人博客,低调大师

常用的 7 款 MySQL 客户端工具,你值得拥有!

云栖号资讯:【点击查看更多行业资讯】在这里您可以找到不同行业的第一手的上云资讯,还在等什么,快来! MySQL的管理维护工具非常多,除了系统自带的命令行管理工具之外,还有许多其他的图形化管理工具,这里我介绍几个经常使用的MySQL图形化管理工具,供大家参考。 1、phpMyAdmin http://www.phpmyadmin.net/ phpMyAdmin是最常用的MySQL维护工具,是一个用PHP开发的基于Web方式架构在网站主机上的MySQL管理工具,支持中文,管理数据库非常方便。不足之处在于对大数据库的备份和恢复不方便。 2、MySQLDumper http://www.mysqldumper.de/en/ MySQLDumper使用PHP开发的MySQL数据库备份恢复程序,解决了使用PHP进行大数据库备份和恢复的问题,数百兆的数据库都可以方便的备份恢复,不用担心网速太慢导致中间中断的问题,非常方便易用。这个软件是德国人开发的,还没有中文语言包。 3、Navicat http://www.navicat.com/ Navicat是一个桌面版MySQL数据库管理和开发工具。和微软SQLServer的管理器很像,易学易用。Navicat使用图形化的用户界面,可以让用户使用和管理更为轻松。支持中文,有免费版本提供。 4、MySQL GUI Tools http://dev.mysql.com/downloads/gui-tools/ MySQL GUI Tools是MySQL官方提供的图形化管理工具,功能很强大,值得推荐,可惜的是没有中文界面。推荐:推荐 4 款 MySQL 调优工具。 5、MySQL ODBC Connector http://dev.mysql.com/downloads/connector/odbc/ MySQL官方提供的ODBC接口程序,系统安装了这个程序之后,就可以通过ODBC来访问MySQL,这样就可以实现SQLServer、Access和MySQL之间的数据转换,还可以支持ASP访问MySQL数据库。 6、MySQL Workbench http://dev.mysql.com/downloads/workbench/ MySQL Workbench是一个统一的可视化开发和管理平台,该平台提供了许多高级工具,可支持数据库建模和设计、查询开发和测试、服务器配置和监视、用户和安全管理、备份和恢复自动化、审计数据检查以及向导驱动的数据库迁移。MySQL Workbench是MySQL AB发布的可视化的数据库设计软件,它的前身是 FabForce 公司的 DDesigner 4。MySQL Workbench 为数据库管理员、程序开发者和系统规划师提供可视化设计、模型建立、以及数据库管理功能。它包含了用于创建复杂的数据建模ER模型,正向和逆向数据库工程,也可以用于执行通常需要花费大量时间和需要的难以变更和管理的文档任务。MySQL工作台可在Windows,Linux和Mac上使用。 7、SQLyog http://sqlyog.en.softonic.com/https://www.webyog.com/product/sqlyog) SQLyog 是一个易于使用的、快速而简洁的图形化管理MYSQL数据库的工具,它能够在任何地点有效地管理你的数据库。SQLyog是业界著名的Webyog公司出品的一款简洁高效、功能强大的图形化MySQL数据库管理工具。使用SQLyog可以快速直观地让您从世界的任何角落通过网络来维护远端的MySQL数据库。 【云栖号在线课堂】每天都有产品技术专家分享!课程地址:https://yqh.aliyun.com/zhibo 立即加入社群,与专家面对面,及时了解课程最新动态!【云栖号在线课堂 社群】https://c.tb.cn/F3.Z8gvnK 原文发布时间:2020-05-26本文作者:KK·Liu先生 本文来自:“互联网架构师 微信公众号”,了解相关信息可以关注“互联网架构师”

优秀的个人博客,低调大师

Seata 客户端需要同时启动 TM 和 RM 吗?

在分析启动部分源码时,我发现 GlobalTransactionScanner 会同时启动 RM 和 TM client,但根据 Seata 的设计来看,TM 负责全局事务的操作,如果一个服务中不需要开启全局事务,此时是不需要启动 TM client的,也就是说项目中如果没有全局事务注解,此时是不是就不需要初始化 TM client 了,因为不是每个微服务,都需要 GlobalTransactional,它此时仅仅作为一个 RM client 而已。 于是我着手将 GlobalTransactionScanner 稍微更改了初始化的规则,由于之前 GlobalTransactionScanner 调用 初始化方法是在 InitializingBean 中的 afterPropertiesSet() 方法中进行,afterPropertySet() 仅仅是当前 bean 初始化后被调用,此时无法得知当前 Spring 容器是否有全局事务注解。 因此我去掉了 InitializingBean,改成了是实现 ApplicationListener,在实例化 bean 的过程中检查是否有 GlobalTransactional 注解的存在,最后在 Spring 容器初始化完成之后再调用 RM 和 TM client 初始化方法,这时候就可以根据项目是否有用到全局事务注解来决定是否启动 TM client 了。 这里附上 PR 地址:https://github.com/seata/seata/pull/1936 随后在 pr 中讨论中得知,目前 Seata 的设计是只有在发起方的 TM 才可以发起 GlobalRollbackRequest,RM 只能发送 BranchReport(false) 上报分支状态个 TC 服务端,无法直接发送 GlobalRollbackRequest 进行全局回滚操作。具体的交互逻辑如下: 那么根据上面的设计模型,自然可以按需启动 TM client 了。 但是 Seata 后面的优化迭代中,还需要考虑的一点是: 当 Provider 服务出现异常时,是否可以直接由 Provider 的 TM client 发起全局回滚?这也就意味着可以缩短分布式事务的周期时间,尽快释放全局锁让其他数据冲突的事务尽早的获取到锁执行。 也就是说在一个全局事务当中,只要有一个 RM client 执行本地事务失败了,直接当前服务的 TM client 发起全局事务回滚,不必要等待发起方的 TM 发起的决议回滚通知了。如果要实现这个优化,那么就需要每个服务都需要同时启动 TM client 和 RM client。 更多精彩文章请关注作者维护的公众号「后端进阶」,这是一个专注后端相关技术的公众号。 关注公众号并回复「后端」免费领取后端相关电子书籍。 欢迎分享,转载请保留出处。

优秀的个人博客,低调大师

开源中国客户端 Android 10 经验适配指南,含代码

我们App的适配从 targetSdkVersion = 26跨版本升级到29,因此会遇到大量的坑,最终的版本配置如下: 现在进入填坑适配指南,包含实际经验代码,绝不照搬翻译文档 1.Region.Op相关异常:java.lang.IllegalArgumentException: Invalid Region.Op - only INTERSECT and DIFFERENCE are allowed 当targetSdkVersion >=Build.VERSION_CODES.P 时调用 canvas.clipPath(path, Region.Op.XXX); 引起的异常,参考源码如下: @Deprecated public boolean clipPath(@NonNull Path path, @NonNull Region.Op op) { checkValidClipOp(op); return nClipPath(mNativeCanvasWrapper, path.readOnlyNI(), op.nativeInt); } private static void checkValidClipOp(@NonNull Region.Op op) { if (sCompatiblityVersion >= Build.VERSION_CODES.P && op != Region.Op.INTERSECT && op != Region.Op.DIFFERENCE) { throw new IllegalArgumentException( "Invalid Region.Op - only INTERSECT and DIFFERENCE are allowed"); } } 我们可以看到当目标版本从Android P开始,Canvas.clipPath(@NonNull Path path, @NonNull Region.Op op) ; 已经被废弃,而且是包含异常风险的废弃API,只有Region.Op.INTERSECT 和 Region.Op.DIFFERENCE 得到兼容,目前不清楚google此举目的如何,仅仅如此简单就抛出异常提示开发者适配,几乎所有的博客解决方案都是如下简单粗暴: if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.P) { canvas.clipPath(path); } else { canvas.clipPath(path, Region.Op.XOR);// REPLACE、UNION 等 } 但我们一定需要一些高级逻辑运算效果怎么办?如小说的仿真翻页阅读效果,解决方案如下,用Path.op代替,先运算Path,再给canvas.clipPath: if(Build.VERSION.SDK_INT >= Build.VERSION_CODES.P){ Path mPathXOR = new Path(); mPathXOR.moveTo(0,0); mPathXOR.lineTo(getWidth(),0); mPathXOR.lineTo(getWidth(),getHeight()); mPathXOR.lineTo(0,getHeight()); mPathXOR.close(); //以上根据实际的Canvas或View的大小,画出相同大小的Path即可 mPathXOR.op(mPath0, Path.Op.XOR); canvas.clipPath(mPathXOR); }else { canvas.clipPath(mPath0, Region.Op.XOR); } 2.明文HTTP限制 当targetSdkVersion >=Build.VERSION_CODES.P 时,默认限制了HTTP请求,并出现相关日志: java.net.UnknownServiceException: CLEARTEXT communication to xxx not permitted by network security policy 第一种解决方案:在AndroidManifest.xml中Application添加如下节点代码 <application android:usesCleartextTraffic="true"> 第二种解决方案:在res目录新建xml目录,已建的跳过 在xml目录新建一个xml文件network_security_config.xml,然后在AndroidManifest.xml中Application添加如下节点代码 android:networkSecurityConfig="@xml/network_config" 名字随机,内容如下: <?xml version="1.0" encoding="utf-8"?> <network-security-config> <base-config cleartextTrafficPermitted="true" /> </network-security-config> 3.Android Q(10)中的媒体资源读写 相关的Android Q 行为变更不做细说,网上大部分博客关于Android Q 适配都在说行为变更,我们将根据实际遇到的问题,实际解决 1、扫描系统相册、视频等,图片、视频选择器都是通过ContentResolver来提供,主要代码如下: private static final String[] IMAGE_PROJECTION = { MediaStore.Images.Media.DATA, MediaStore.Images.Media.DISPLAY_NAME, MediaStore.Images.Media._ID, MediaStore.Images.Media.BUCKET_ID, MediaStore.Images.Media.BUCKET_DISPLAY_NAME}; Cursor imageCursor = mContext.getContentResolver().query( MediaStore.Images.Media.EXTERNAL_CONTENT_URI, IMAGE_PROJECTION, null, null, IMAGE_PROJECTION[4] + " DESC"); String path = imageCursor.getString(imageCursor.getColumnIndexOrThrow(IMAGE_PROJECTION[0])); String name = imageCursor.getString(imageCursor.getColumnIndexOrThrow(IMAGE_PROJECTION[1])); int id = imageCursor.getInt(imageCursor.getColumnIndexOrThrow(IMAGE_PROJECTION[2])); String folderPath = imageCursor.getString(imageCursor.getColumnIndexOrThrow(IMAGE_PROJECTION[3])); String folderName = imageCursor.getString(imageCursor.getColumnIndexOrThrow(IMAGE_PROJECTION[4])); //Android Q 公有目录只能通过Content Uri + id的方式访问,以前的File路径全部无效,如果是Video,记得换成MediaStore.Videos if(Build.VERSION.SDK_INT >= Build.VERSION_CODES.Q){ path = MediaStore.Images.Media .EXTERNAL_CONTENT_URI .buildUpon() .appendPath(String.valueOf(id)).build().toString(); } 2、判断公有目录文件是否存在,自Android Q开始,公有目录File API都失效,不能直接通过new File(path).exists();判断公有目录文件是否存在,正确方式如下: public static boolean isAndroidQFileExists(Context context, String path){ if (context == null) { return false; } AssetFileDescriptor afd = null; ContentResolver cr = context.getContentResolver(); try { Uri uri = Uri.parse(path); afd = cr.openAssetFileDescriptor(Uri.parse(path), "r"); if (afd == null) { return false; } else { close(afd); } } catch (FileNotFoundException e) { return false; }finally { close(afd); } return true; } 3、保存或者下载文件到公有目录,保存Bitmap同理,如Download,MIME_TYPE类型可以自行参考对应的文件类型,这里只对APK作出说明 public static void copyToDownloadAndroidQ(Context context, String sourcePath, String fileName, String saveDirName){ ContentValues values = new ContentValues(); values.put(MediaStore.Downloads.DISPLAY_NAME, fileName); values.put(MediaStore.Downloads.MIME_TYPE, "application/vnd.android.package-archive"); values.put(MediaStore.Downloads.RELATIVE_PATH, "Download/" + saveDirName.replaceAll("/","") + "/"); Uri external = MediaStore.Downloads.EXTERNAL_CONTENT_URI; ContentResolver resolver = context.getContentResolver(); Uri insertUri = resolver.insert(external, values); if(insertUri == null) { return; } String mFilePath = insertUri.toString(); InputStream is = null; OutputStream os = null; try { os = resolver.openOutputStream(insertUri); if(os == null){ return; } int read; File sourceFile = new File(sourcePath); if (sourceFile.exists()) { // 文件存在时 is = new FileInputStream(sourceFile); // 读入原文件 byte[] buffer = new byte[1444]; while ((read = is.read(buffer)) != -1) { os.write(buffer, 0, read); } is.close(); os.close(); } } catch (Exception e) { e.printStackTrace(); } finally { close(is,os); } } 4、保存图片相关 /** * 通过MediaStore保存,兼容AndroidQ,保存成功自动添加到相册数据库,无需再发送广告告诉系统插入相册 * * @param context context * @param sourceFile 源文件 * @param saveFileName 保存的文件名 * @param saveDirName picture子目录 * @return 成功或者失败 */ public static boolean saveImageWithAndroidQ(Context context, File sourceFile, String saveFileName, String saveDirName) { String extension = BitmapUtil.getExtension(sourceFile.getAbsolutePath()); ContentValues values = new ContentValues(); values.put(MediaStore.Images.Media.DESCRIPTION, "This is an image"); values.put(MediaStore.Images.Media.DISPLAY_NAME, saveFileName); values.put(MediaStore.Images.Media.MIME_TYPE, "image/png"); values.put(MediaStore.Images.Media.TITLE, "Image.png"); values.put(MediaStore.Images.Media.RELATIVE_PATH, "Pictures/" + saveDirName); Uri external = MediaStore.Images.Media.EXTERNAL_CONTENT_URI; ContentResolver resolver = context.getContentResolver(); Uri insertUri = resolver.insert(external, values); BufferedInputStream inputStream = null; OutputStream os = null; boolean result = false; try { inputStream = new BufferedInputStream(new FileInputStream(sourceFile)); if (insertUri != null) { os = resolver.openOutputStream(insertUri); } if (os != null) { byte[] buffer = new byte[1024 * 4]; int len; while ((len = inputStream.read(buffer)) != -1) { os.write(buffer, 0, len); } os.flush(); } result = true; } catch (IOException e) { result = false; } finally { Util.close(os, inputStream); } return result; } 4.EditText默认不获取焦点,不自动弹出键盘 该问题出现在targetSdkVersion >=Build.VERSION_CODES.P 情况下,且设备版本为Android P以上版本,目前我们没有从源码中查到相关判断改动,解决方法在onCreate中加入如下代码: mEditText.post(() -> { mEditText.requestFocus(); mEditText.setFocusable(true); mEditText.setFocusableInTouchMode(true); }); 5.Only fullscreen activities can request orientation 异常 该问题出现在targetSdkVersion >=Build.VERSION_CODES.O_MR1 ,也就是 API 27,当设备为Android 26时(27以上已经修复,也许google觉得不妥当,又改回来了),如果非全面屏透明activity固定了方向,则出现该异常,但是当我们在小米、魅族等Android 26机型测试的时候,并没有该异常,华为机型则报该异常,这是何等的卧槽。。。没办法,去掉透明style或者去掉固定方向代码即可,其它无解 6.安装APK Intent及其它文件相关Intent /* * 自Android N开始,是通过FileProvider共享相关文件,但是Android Q对公有目录 File API进行了限制 * 从代码上看,又变得和以前低版本一样了,只是必须加上权限代码Intent.FLAG_GRANT_READ_URI_PERMISSION */ private void installApk() { if(Build.VERSION.SDK_INT >= Build.VERSION_CODES.Q){ //适配Android Q,注意mFilePath是通过ContentResolver得到的,上述有相关代码 Intent intent = new Intent(Intent.ACTION_VIEW); intent.setDataAndType(Uri.parse(mFilePath) ,"application/vnd.android.package-archive"); intent.setFlags(Intent.FLAG_ACTIVITY_NEW_TASK); intent.addFlags(Intent.FLAG_GRANT_READ_URI_PERMISSION); startActivity(intent); return ; } File file = new File(saveFileName + "osc.apk"); if (!file.exists()) return; Intent intent = new Intent(Intent.ACTION_VIEW); if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.N) { intent.setFlags(Intent.FLAG_ACTIVITY_NEW_TASK); intent.addFlags(Intent.FLAG_GRANT_READ_URI_PERMISSION); Uri contentUri = FileProvider.getUriForFile(getApplicationContext(), "net.oschina.app.provider", file); intent.setDataAndType(contentUri, "application/vnd.android.package-archive"); } else { intent.setDataAndType(Uri.fromFile(file), "application/vnd.android.package-archive"); intent.setFlags(Intent.FLAG_ACTIVITY_NEW_TASK); } startActivity(intent); } 我们APK开发实践中暂时遇到的坑就这些,当然Android Q的改动是相当大的,例如还有App私有沙箱文件、定位权限和后台弹出Activity限制,这些都必须根据自身实践去踩坑适配,有条件的尽可能去阅读官方文档,参考改进。

资源下载

更多资源
Mario

Mario

马里奥是站在游戏界顶峰的超人气多面角色。马里奥靠吃蘑菇成长,特征是大鼻子、头戴帽子、身穿背带裤,还留着胡子。与他的双胞胎兄弟路易基一起,长年担任任天堂的招牌角色。

Spring

Spring

Spring框架(Spring Framework)是由Rod Johnson于2002年提出的开源Java企业级应用框架,旨在通过使用JavaBean替代传统EJB实现方式降低企业级编程开发的复杂性。该框架基于简单性、可测试性和松耦合性设计理念,提供核心容器、应用上下文、数据访问集成等模块,支持整合Hibernate、Struts等第三方框架,其适用范围不仅限于服务器端开发,绝大多数Java应用均可从中受益。

Rocky Linux

Rocky Linux

Rocky Linux(中文名:洛基)是由Gregory Kurtzer于2020年12月发起的企业级Linux发行版,作为CentOS稳定版停止维护后与RHEL(Red Hat Enterprise Linux)完全兼容的开源替代方案,由社区拥有并管理,支持x86_64、aarch64等架构。其通过重新编译RHEL源代码提供长期稳定性,采用模块化包装和SELinux安全架构,默认包含GNOME桌面环境及XFS文件系统,支持十年生命周期更新。

WebStorm

WebStorm

WebStorm 是jetbrains公司旗下一款JavaScript 开发工具。目前已经被广大中国JS开发者誉为“Web前端开发神器”、“最强大的HTML5编辑器”、“最智能的JavaScript IDE”等。与IntelliJ IDEA同源,继承了IntelliJ IDEA强大的JS部分的功能。

用户登录
用户注册