首页 文章 精选 留言 我的

精选列表

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

基于umeng官方php sdk v1.4,支持Laravel5以及Lumen5

安装 composer require zzl/umeng Laravel 5.* 配置 打开config目录下的app.php文件,找到provider,添加如下代码: 'provider' => [ Zzl\Umeng\UmengServiceProvider::class, ], 配置alias: 'aliases' => [ 'Umeng' => Zzl\Umeng\Facades\Umeng::class, ], 生成配置文件: php artisan vendor:publish 在配置文件umeng.php中填入appkey以及master_secret既可完成配置 在Lumen 5.*中配置 打开bootstrap目录下的app.php文件,注册provider: $app->register(Zzl\Umeng\UmengServiceProvider::class); 配置alias: class_alias('Zzl\Umeng\Facades\Umeng','Umeng'); 生成配置文件: php artisan vendor:publish 在配置文件umeng.php中填入appkey以及master_secret既可完成配置 用法 Android用法: use Umeng; $device_token = 'xxxx'; $predefined = array('ticker' => 'android ticker' ,...); $extraField = array(); //other extra filed Umeng::android()->sendUnicast($device_token,$predefined,$extraField); //单播 IOS用法: use Umeng; $device_token = 'xxxx'; $predefined = array('alert' => 'ios alert' ,...); $customField = array(); //other custom filed Umeng::ios()->sendUnicast($device_token,$predefined,$customField); //单播 Api 说明: Android API跟 IOS一样 sendBroadcast($predefined = [], $extraField = []); //广播 sendUnicast($device_tokens = '', $predefined= [], $extraField = []); //单播 sendListcast($device_tokens = '', $predefined= [], $extraField = []); //列播 sendFilecast($fileContents = '', $predefined= [],$extraField = []); //文件播 sendGroupcast($filter = [], $predefined= [], $extraField = []); //组播 sendCustomizedcast($alias = '', $alias_type = '', $predefined= [], $extraField = []); //自定义播,通过alias sendCustomizedcastFileId($file_contents = '', $predefined= [], $extraField = []); //自定义播,通过file_id Exception 程序不处理异常,可根据业务情况自行处理, 若抛出异常,可通过 e->getHttpCode() 获取http状态码, 通过 e->getErrCode()获取umeng返回的错误码. 使用过程中若出错,可自行查看Laravel或Lumen的Log日志

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

每周新品|云市场官方小二推荐值得买清单(有图有真相)

岁末将至,阿里云云市场7大类目、3000余款产品是不是让您挑花了眼。每周新品这个栏目就为各位用户甄选最值得买的产品。本周我们特意邀请阿里云云市场各类目小二精选本类目最值得推荐的新品,汇聚成值得买清单。 点击购买>译云机器翻译-翻译测试接口(公测) 点击购买>京颐云HIS·SaaS版 点击购买>Oracle安装、配置、故障排除、迁移、调优代维服务 点击购买>绿盟网站安全评估服务 点击购买>【微信网站】微网站建设微信公众号定制开发手机微官网制作购物商城设计 Udesk,智能在线客服系统 Udesk全渠道客服系统,将在线客服,呼叫中心,工单,邮件,微信微博信息统一到一个平台进行客服管理,大幅度提升客服效率,用户满意度。 优势特色:1、无需下载与安装;2、快速部署,接入企业系统;3、无需硬件设备。 点击购买>Udes

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

Android官方开发文档Training系列课程中文版:管理设备的睡眠状态

原文地址:http://android.xsoftlab.net/training/scheduling/index.html 引言 当Android设备处于闲置状态时,它的屏幕首先会变暗,接着会关闭屏幕,最后会将CPU关闭。这些举措可以防止设备的电量迅速被耗尽。但是当APP需要的话,还是会有例外情况: 游戏类APP或者视频类APP需要保持屏幕常亮。 有一部分APP或许不需要屏幕保持常亮,但是它们需要CPU继续保持运转,直到它们的任务执行完毕。 这节课主要学习如何在需要的时候保持设备的唤醒状态而又不至于非常耗电。 保持设备的唤醒状态 为了避免迅速将电量耗光,Android设备会在进入闲置状态后紧接着进入睡眠状态。不过,还是有一些例外情况的:它们需要保持屏幕常亮或者是保持CPU持续运转状态以便完成某些任务。 具体采用什么样的方式这取决于APP的需求。不过,有一条规则就是尽量采取最轻量级的方法,尽可能少的消耗系统资源。 保持屏幕常亮 某些APP比如游戏类APP或者视频类APP需要保持屏幕常亮。要做到这一点只需要在Activity中使用FLAG_KEEP_SCREEN_ON就可以,不过千万不要在服务或者其它组件中使用该标志: public class MainActivity extends Activity { @Override protected void onCreate(Bundle savedInstanceState) { super.onCreate(savedInstanceState); setContentView(R.layout.activity_main); getWindow().addFlags(WindowManager.LayoutParams.FLAG_KEEP_SCREEN_ON); } ... } 这种方法的优势在于:它不要指定特殊权限,系统会将APP之间的状态切换处理好,也不需要担心有关释放无用资源的问题。 另一个实现方式就是在布局文件中使用android:keepScreenOn属性: <RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android" android:layout_width="match_parent" android:layout_height="match_parent" android:keepScreenOn="true"> ... </RelativeLayout> android:keepScreenOn=”true”的作用效果与使用FLAG_KEEP_SCREEN_ON的效果等同。你可以选择最合适的方式。使用标志的优势在于可以动态的清除该标志的状态,以便于屏幕可以转入关闭状态。 Note: 除非可以肯定屏幕不再需要保持常亮,否则不需要我们自己专门去清除该标志。WindowManager会严格把关这些事情:APP转入后台时,APP转入前台时。但是如果你明确要清除该标志以便屏幕可以转入关闭状态,那么可以使用clearFlags():getWindow().clearFlags(WindowManager.LayoutParams.FLAG_KEEP_SCREEN_ON) 保持CPU的运行 如果APP希望在系统转入睡眠状态之前完成一些事情,那么可以使用PowerManager系统服务中的WakeLock特性。WakeLock可以使APP控制设备的电源状态。 因为持有WakeLock对象可以直接与电源交互,所以只能在必要的时候使用WakeLock。绝不要在Activity中使用WakeLock。就像上面说的那样,如果希望保持屏幕常亮,只需要使用FLAG_KEEP_SCREEN_ON就可以。 使用WakeLock的合理场景就是后台服务。再强调一次,使用时应当以最小限度使用该标志,因为它会直接影响到电池的电量。 如果要使用WakeLock,首先需要在清单文件中添加WakeLock的权限: <uses-permission android:name="android.permission.WAKE_LOCK" /> 如果APP还包括了一个与服务做相关工作的广播接收器,那么可以通过WakefulBroadcastReceiver来管理WakeLock。这是一种非常理想的方案。如果APP没有那样的情况,那么也可以使用下面的方法: PowerManager powerManager = (PowerManager) getSystemService(POWER_SERVICE); Wakelock wakeLock = powerManager.newWakeLock(PowerManager.PARTIAL_WAKE_LOCK, "MyWakelockTag"); wakeLock.acquire(); 如果要释放WakeLock,调用wakelock.release()就好。它会释放你所持有的CPU资源。在任务完成后做这项工作是很重要的,因为这可以防止电池电量被迅速耗光。 使用WakefulBroadcastReceiver 广播接收器与服务的结合使用非常易于管理后台任务的生命周期。 WakefulBroadcastReceiver是一种特殊的广播接收器:它可以创建并管理APP的PARTIAL_WAKE_LOCK。在设备即将转入睡眠状态时,WakefulBroadcastReceiver会将该信号发给服务(通常是IntentService)。如果在收到广播后没有持有WakeLock,那么可以在工作完成之前设备就会转入睡眠状态。这就会导致任务不能及时完成,这并不是我们想看到的。 WakefulBroadcastReceiver用法的第一步就是将其添加到清单文件中,与其它广播接收器的添加方式一样: <receiver android:name=".MyWakefulReceiver"></receiver> 第二步就是使用startWakefulService()方法来启动MyIntentService。这个方法除了在启动时WakefulBroadcastReceiver持有了一个WakeLock外,其它的都与startService()很相似。在startWakefulService()中所使用的Intent被隐式的携带了一个WakeLock。 public class MyWakefulReceiver extends WakefulBroadcastReceiver { @Override public void onReceive(Context context, Intent intent) { // Start the service, keeping the device awake while the service is // launching. This is the Intent to deliver to the service. Intent service = new Intent(context, MyIntentService.class); startWakefulService(context, service); } } 在服务结束时,要使用MyWakefulReceiver.completeWakefulIntent()将WakeLock释放。completeWakefulIntent()方法使用了被WakefulBroadcastReceiver传递过来的Intent对象: public class MyIntentService extends IntentService { public static final int NOTIFICATION_ID = 1; private NotificationManager mNotificationManager; NotificationCompat.Builder builder; public MyIntentService() { super("MyIntentService"); } @Override protected void onHandleIntent(Intent intent) { Bundle extras = intent.getExtras(); // Do the work that requires your app to keep the CPU running. // ... // Release the wake lock provided by the WakefulBroadcastReceiver. MyWakefulReceiver.completeWakefulIntent(intent); } }

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

美国人口普查局去年遭受入侵,官方称普查数据未受影响

根据美国监察长办公室 (OIG) 最近披露的一份报告显示,美国人口普查局使用的Citrix设备存在零日漏洞,该漏洞导致服务器在2021年1月11日遭到攻击,黑客利用未修补的 Citrix ADC 零日漏洞入侵服务器。 报告中表明,被攻击的服务器向该局提供远程访问能力,使其工作人员能够访问生产、开发和实验室网络。被攻击后,系统人员表示,这些服务器无法接入2020年十年一次的人口普查网络。 攻击行为未全部成功 虽然攻击者能够破坏该局的服务器,并建立了允许他们远程执行恶意代码的流氓管理员帐户,幸运的是他们无法部署后门来保持对服务器的长期访问。据 OIG 称,此次美国人口普查局未能及时处理关键漏洞,才导致其服务器易受攻击。此外,在服务器被攻陷后,该局也未能及时发现和报告攻击行为,没有维护足够多的系统日志,这些行为都阻碍了事件的调查。 美国监察长办公室 (OIG)称,没有迹象表明2020年十年人口普查系统受到任何损害,也没有任何其他的恶意行为影响 2020 年的十年人口统计数据。此外,美国人口普查局代表公众维护和管理的系统或数据没有受到损害、操纵或丢失。 报告中还表明,在2020年1月13日,黑客对远程访问服务器攻击时,试图与远程服务器进行通信,美国人口普查局的防火墙已经阻止了部分攻击。然而,直到2周多后的1月28日,该局才知道服务器被攻击者入侵。 攻击者利用了一个严重的 Citrix 漏洞 OIG提到该漏洞是在2019年12月17日披露的,因此有可能将其准确定位为CVE-2019-19781,这是一个影响Citrix的应用程序交付控制器(ADC)、网关和SD-WAN WANOP设备的严重漏洞。不幸的是OIG的报告中删除了漏洞和软件供应商的名字,显示被删除的供应商是Citrix,但是人口普查局对攻击的回应没有被修改。 美国人口调查局称,因为 COVID-19和缺少工程师(已经满负荷为联邦政府的客户提供支持),迁移工作未完成。 如果成功利用CVE-2019-19781漏洞,远程攻击者可以在未打补丁的服务器上执行任意代码,无需身份验证即可访问内部网络。 仍在积极利用的 Citrix 漏洞 Citrix于2019年12月17日披露了安全漏洞,并提供了缓解措施,并于2020年1月24 日发布了解决该漏洞的产品更新。 然而,在1月8日检测到Citrix服务器存在漏洞后两天,针对CVE-2019-19781的概念验证漏洞被公开。攻击者趁机开始攻击未打补丁的 Citrix 服务器,安全研究人员观察到攻击者在受感染的服务器上部署恶意软件,包括Sodinokibi和Ragnarok勒索软件负载等。 今年2月,DoppelPaymer勒索软件团伙还利用同样的漏洞,入侵了法国的一家电信公司Bretagne Télécom的网络。自那以后,CVE-2019-19781漏洞被美国联邦调查局(FBI)列入过去两年的头号目标漏洞名单,并被美国国家安全局(NSA)列入黑客滥用的前五名漏洞。

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

中小企业如何建官方网站---推荐阿里云自营建站服务

近期准备使用ThinkCMF管理架构搭建一个新的资讯网站,已经拥有的两个域名全是在阿里购买以及备案的,现在需要选择一个适合的云服务器,所以就逛了逛阿里云,看看对于建站方面有没有什么推荐,然后无意中发现阿里云推出的云建站服务,这对于中小企业来说简直是福利了,基本上是个标准的公司都开始有了自己的官网,笑话,没有官网客户怎么了解你的产品,有可能就是因为你的官网设计的标准,大气,客户就会对你的信任度增加,从而促进一笔不小的订单,这都是有可能的啊。 然鹅,现实的问题是,不是所有的公司都是互联网公司,不是每个公司都有软件开发人员的,所以建站难免成了一个障碍,很多公司可能会选择花钱找私人承包,这样的选择弊端太多了,① 价格不透明 ② 后期维护不方便 ③ 容易被攻击 等等问题你还放心的下吗? 阿里云企业建站服务介绍 云速成美站,标配阿里云空间,PC站+手机站+微信公众号+小程序一应俱全,只要你会打字就可以完成建站操作,难易程度大概和制作一个PPT差不多,根本没有什么门槛。阿里云还提供千套企业模板,风格颜色随心选择,40余种功能控件,按需搭配使用,建站就是这么简单! 云企业官网,阿里云会为客户量身打造,一站式标准化建站服务,满足企业建站所需。从咨询到购买,标准价格,标准功能配置,足不出户,轻松搞定,购买成功后,应用标准化服务流程,客户可享受从网站策划到上线的全程定值服务。更有项目经理为客户整理需求,搭建网站架构,预置网站内容;设计师一对一进行视觉美化,风格由客户选择: 高大上?满足建筑美?满足极简风?满足全部建站过程,无需客户亲自操作,简单高效,品质有保障,毕竟大公司,值得信赖,哈哈哈。 为什么选择阿里云自营建站服务? 选择小公司,后期维护难,安全系数低,轻易被攻击、挂马,而且网站的后续升级改版同样比较麻烦,运营人员需要不断的联系程序人员,费钱还不省心。我们选择阿里云建站服务,安全省心,花钱不再担心打水漂! 阿里云建站全面应用云计算,标配HTTPS,网站安全稳定访问快。网站后台可视化操作,每季度版本更新,免费享用,轻松简单易维护。阿里云的承诺是只有你想不到,没有他们办不到,建站就找阿里云,和传统建站说拜拜。 想要了解更多的可以自己到官网去看看详细内容,选择一个大公司毕竟还是比较靠谱的事情:https://www.aliyun.com

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

中小企业如何建官方网站 | 推荐阿里云自营建站服务

近期准备使用ThinkCMF管理架构搭建一个新的资讯网站,已经拥有的两个域名全是在阿里购买以及备案的,现在需要选择一个适合的云服务器,所以就逛了逛阿里云,看看对于建站方面有没有什么推荐,然后无意中发现阿里云推出的云建站服务,这对于中小企业来说简直是福利了,基本上是个标准的公司都开始有了自己的官网,笑话,没有官网客户怎么了解你的产品,有可能就是因为你的官网设计的标准,大气,客户就会对你的信任度增加,从而促进一笔不小的订单,这都是有可能的啊。 然鹅,现实的问题是,不是所有的公司都是互联网公司,不是每个公司都有软件开发人员的,所以建站难免成了一个障碍,很多公司可能会选择花钱找私人承包,这样的选择弊端太多了,① 价格不透明 ② 后期维护不方便 ③ 容易被攻击 等等问题你还放心的下吗? 阿里云企业建站服务介绍 云速成美站,标配阿里云空间,PC站+手机站+微信公众号+小程序一应俱全,只要你会打字就可以完成建站操作,难易程度大概和制作一个PPT差不多,根本没有什么门槛。阿里云还提供千套企业模板,风格颜色随心选择,40余种功能控件,按需搭配使用,建站就是这么简单! 云企业官网,阿里云会为客户量身打造,一站式标准化建站服务,满足企业建站所需。从咨询到购买,标准价格,标准功能配置,足不出户,轻松搞定,购买成功后,应用标准化服务流程,客户可享受从网站策划到上线的全程定值服务。更有项目经理为客户整理需求,搭建网站架构,预置网站内容;设计师一对一进行视觉美化,风格由客户选择: 高大上?满足建筑美?满足极简风?满足全部建站过程,无需客户亲自操作,简单高效,品质有保障,毕竟大公司,值得信赖,哈哈哈。 为什么选择阿里云自营建站服务? 选择小公司,后期维护难,安全系数低,轻易被攻击、挂马,而且网站的后续升级改版同样比较麻烦,运营人员需要不断的联系程序人员,费钱还不省心。我们选择阿里云建站服务,安全省心,花钱不再担心打水漂! 阿里云建站全面应用云计算,标配HTTPS,网站安全稳定访问快。网站后台可视化操作,每季度版本更新,免费享用,轻松简单易维护。阿里云的承诺是只有你想不到,没有他们办不到,建站就找阿里云,和传统建站说拜拜。 想要了解更多的可以自己到官网去看看详细内容,选择一个大公司毕竟还是比较靠谱的事情:https://www.aliyun.com

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

Android官方开发文档Training系列课程中文版:Activity测试之UI组件测试

原文地址:http://android.xsoftlab.net/training/activity-testing/activity-ui-testing.html 一般来说,正因为Activity含有UI组件,所以使得用户可以与程序交互。这节课将会介绍如何测试Activity中的Button组件。在课程学习之后便可以使用相同的方法对其它UI组件进行测试。 Note:这节课中所涉及的UI测试被称为白盒测试,因为开发者本身持有被测试的源代码。Android设备框架适用于UI组件的白盒测试。另一种测试类型被称为黑盒测试,因为不能够得到程序的源代码,故此得名。这种测试适用于与其它APP或系统交互的测试情况。黑盒测试在这里并不会涵盖。有关更多如何执行黑盒测试的相关内容,请参见UI测试指南。 创建UI测试用例 虽然Activity运行于UI线程,但是测试程序本身是运行在子线程中的。这意味着,虽然TestAPP可以引用UI线程的对象,但是如果要更改这些对象的属性或者发送事件给UI线程,那么将会得到一个WrongThreadException错误。 为了可以安全的发送Intent到Activity或者在UI线程中运行测试方法,开发者可以使测试类继承于ActivityInstrumentationTestCase2类。 设置测试先决条件 当为UI测试设置先决条件时,则需要在setUp()方法中指定TouchMode。设置TouchMode为true可以使后面的测试方法在自动化点击UI组件时防止真正点击(例如,测试Button只是调用了它的onclick方法)。另外要确保在调用getActivity()方法之前调用了setActivityInitialTouchMode()方法。 例如: public class ClickFunActivityTest extends ActivityInstrumentationTestCase2 { ... @Override protected void setUp() throws Exception { super.setUp(); setActivityInitialTouchMode(true); mClickFunActivity = getActivity(); mClickMeButton = (Button) mClickFunActivity .findViewById(R.id.launch_next_activity_button); mInfoTextView = (TextView) mClickFunActivity.findViewById(R.id.info_text_view); } } 添加测试方法 一般需要测试的点会包含以下部分: 当Activity启动时,验证Button的布局是否显示正确。 验证TextView在初始化时是否是隐藏的。 验证Button按下后,TextView上的文本是否变为了期望的值。 下面将会演示如何测试以上部分: 验证Button的布局参数 开发者可能需要以下代码来验证Button的布局是否正确: @MediumTest public void testClickMeButton_layout() { final View decorView = mClickFunActivity.getWindow().getDecorView(); ViewAsserts.assertOnScreen(decorView, mClickMeButton); final ViewGroup.LayoutParams layoutParams = mClickMeButton.getLayoutParams(); assertNotNull(layoutParams); assertEquals(layoutParams.width, WindowManager.LayoutParams.MATCH_PARENT); assertEquals(layoutParams.height, WindowManager.LayoutParams.WRAP_CONTENT); } 在调用assertOnScreen()方法时,应当将rootView以及需要验证的View传递进去。如果需要验证的View没有在rootView中出现,那么判断方法会抛出一个AssertionFailedError异常。 开发者还可以通过Button的布局参数来验证Button的布局是否正确,然后通过判断方法来验证Button的高宽是否是期望中的值。 @MediumTest注解说明了这个测试方法应当如何分类。如何分类取决于测试方法的执行时间。 验证TextView的布局参数 开发者也可能需要通过以下代码来验证TextView在初始化时是否是隐藏的: @MediumTest public void testInfoTextView_layout() { final View decorView = mClickFunActivity.getWindow().getDecorView(); ViewAsserts.assertOnScreen(decorView, mInfoTextView); assertTrue(View.GONE == mInfoTextView.getVisibility()); } 开发者可以通过getDecorView()方法获得Activity的DecorView引用。DecorView在布局层级中属于最高等级的ViewGroup. 验证Button的行为 开发者可以根据以下测试方法来验证在Button按下后TextView是否变为可见状态。 @MediumTest public void testClickMeButton_clickButtonAndExpectInfoText() { String expectedInfoText = mClickFunActivity.getString(R.string.info_text); TouchUtils.clickView(this, mClickMeButton); assertTrue(View.VISIBLE == mInfoTextView.getVisibility()); assertEquals(expectedInfoText, mInfoTextView.getText()); } 为了可以自动点击Button,需要调用clickView()方法。该方法需要传入测试用例的引用以及对应Button的引用。 Note: 辅助类TouchUtils提供了一些用于模拟交互的简单方法,开发者可以使用这些方法来模拟点击,拖拽等事件。 Note: TouchUtils中的方法用于从测试线程向UI线程中发送事件。开发者最好不要在UI线程中直接调用TouchUtils的相关方法,否则会引起WrongThreadException异常. 测试注解 以下注解可以用来标明测试方法的大小: @SmallTest @MediumTest @LargeTest 一般来说,一个只有几毫秒的剪短测试一般应该标为@SmallTest。稍长一点的,大概100毫秒左右的,通常应该标为@MediumTest或@LargeTest,测试的执行时间通常取决于是否需要访问本地资源或者网络资源。 开发者应当通过注解来标记测试方法,以便更好的组织、运行测试。

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

Android官方开发文档Training系列课程中文版:Activity测试之创建运行测试

原文地址:http://android.xsoftlab.net/training/activity-testing/activity-basic-testing.html 为了验证在布局与功能上没有差池,很重要的一点就是需要为每个Activity创建对应的测试类。对每个测试类还需要创建单独的测试用例,这其中包含测试环境,测试条件以及对Activity测试的测试方法。实现这些便可以进行测试并获知结果。如果其中一项测试失败了,这便意味着在代码中可能存在潜在的问题。 创建测试用例 Activity测试都以结构化的方式实现。要确保将所有的测试放在一个单独的包中,与被测试代码区别开来。 依照惯例,测试包的包名应当由应用的包名+后缀”.tests”组成。在完成测试包的创建之后,添加一个Java类以用于测试。依照惯例,该类的名称应当由要测试的类的类名+后缀”Test”组成。 在Eclipse中创建测试用例的步骤如下: a.在工程中新建一个包。 b.设置包名为< your_app_package_name>.tests(例如,com.example.android.testingfun.tests),并点击Finish。 c.在该包名下创建一个类。 d.设置类名为< your_app_activity_name>Test(例如,MyFirstTestActivityTest),并点击Finish。 设置测试先决条件 测试先决条件由一系列用于测试的对象组成。设置这些先决条件需要重写setUp()方法以及tearDown()方法。TestRunner会在测试之前调用setUp()方法,在测试结束之后调用tearDown()方法。开发者可以通过这两个方法来确保测试被正常初始化以及可以确保在测试结束之后可以及时清理。 在Eclipse中设置测试先决条件: 1.将上面创建好的测试类继承于ActivityTestCase的任一子类。例如: public class MyFirstTestActivityTest extends ActivityInstrumentationTestCase2<MyFirstTestActivity> { 2.接下来,在这个类的内部添加构造方法以及setUp()方法,并添加要测试的Activity的变量声明。例如: public class MyFirstTestActivityTest extends ActivityInstrumentationTestCase2<MyFirstTestActivity> { private MyFirstTestActivity mFirstTestActivity; private TextView mFirstTestText; public MyFirstTestActivityTest() { super(MyFirstTestActivity.class); } @Override protected void setUp() throws Exception { super.setUp(); mFirstTestActivity = getActivity(); mFirstTestText = (TextView) mFirstTestActivity .findViewById(R.id.my_first_test_text_view); } } 构造方法会在类初始化时由TestRunner调用,而setUp()方法则会在开始测试之前调用。 通常情况下,在setUp()方法内,应当实现以下内容: - 调用父类的setUp()方法。 - 通过以下步骤初始化先决条件: - 定义实例变量用于存储先决条件的状态。 - 创建并存储接下来要测试的Activity的引用。 - 持有Activity中需要进行测试的UI组件的引用。 可以通过getActivity()获取要测试的Activity的引用。 添加测试条件 在进行测试之前,还有一个步骤就是需要验证前一步是否设置正确,以及需要测试的对象是否已被正确的实例化、初始化。这样的话,便不需要确认测试本身是否有误,因为测试的先决条件已经发生了错误。依照惯例,用于验证先决条件的方法被称为testPreconditions(). 例如: public void testPreconditions() { assertNotNull(“mFirstTestActivity is null”, mFirstTestActivity); assertNotNull(“mFirstTestText is null”, mFirstTestText); } 其中的判断方法来自于JUnit的Assert类。通常情况下可以使用这些判断方法来验证需要测试的指定条件是否为true。 - 如果条件为false,那么判断方法会抛出一个AssertionFailedError异常。该异常由TestRunner抛出。如果判断失败,那么可以通过判断方法的第一个参数得知是哪个条件失败。 - 如果条件为true,那么测试会顺利执行。 在这两种情况中,TestRunner会继续执行其它的判断方法。 添加测试方法 接下来,添加测试方法来验证Activity的布局与功能。 例如,如果Activity包含了一个TextView,你可以像下面这样添加一个测试方法来验证该TextView的文本是否正确: public void testMyFirstTestTextView_labelText() { final String expected = mFirstTestActivity.getString(R.string.my_first_test); final String actual = mFirstTestText.getText().toString(); assertEquals(expected, actual); } testMyFirstTestTextView_labelText()方法用于检测TextView的默认文本与定义在string.xml中的文本是否一致。 Note: 当命名测试方法时,可以使用下划线来分开要测试的内容,这种编写风格可以更容易明确测试的内容。 要执行比较,将期望的值与实际的值传给assertEquals()方法。如果两个值不相等,那么将会抛出一个AssertionFailedError异常。 如果添加testPreconditions()方法,那么请将测试代码放在testPreconditions()之后。 构建运行测试 在Eclipse中进行代码测试非常容易。 请执行以下步骤: 1.将Android设备连接到计算机。打开Setting菜单,选择Developer选项,并确保USB调试模式已开启。 2.在测试的类中选择RunAs > Android Junit Test. 3.在Android设备选择对话框中,选择刚刚连接好的设备,点击OK。 4.在JUnit界面中,验证测试是否通过。

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

Android官方开发文档Training系列课程中文版:Activity测试之测试环境配置

原文地址:http://android.xsoftlab.net/training/activity-testing/index.html 引言 开发者应当将测试作为应用开发周期的一部分。良好的测试用例可以帮助开发者及早的发现Bug,同时也可以增强开发者对代码的信心。 测试用例定义了一系列对象与方法,使各个测试可以独自进行。测试用例既可以组合运行,也可以重复进行。 这节课的课程将会介绍如何使用Android的自定义测试框架进行测试,该框架基于很受欢迎的JUnit框架。开发者可以通过编写测试用例来验证程序的某些功能,也可以检查不同设备的兼容性。 配置测试环境 在开始进行测试之前,开发者首先应当配置测试环境。这节课将会学习如何通过命令行来配置基于Gradle的测试用例。 配置Eclipse Note: 因为目前使用Eclipse开发所占的比例已经很少了,所以接下来的翻译凡涉及到Eclipse的,文字描述都极为精简。需要了解的请查看原文。 配置命令行 如果开发者使用的是Gradle 1.6或以上的版本,那么可以使用Gradle Wrapper来构建运行测试用例。要确保在gradle.build文件中,defaultConfig下的minSdkVersion属性设置的是8以上的值(含)。 要运行基于Gradle Wrapper的测试,需要执行以下步骤: 1.将物理设备连接到计算机上。 2.在工程目录下运行以下命令: ./gradlew build connectedCheck 学习更多关于使用Gradle进行Android测试的相关内容,请参见Gradle Plugin User Guide.

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

Android官方开发文档Training系列课程中文版:布局性能优化之布局复用

原文地址:http://android.xsoftlab.net/training/improving-layouts/reusing-layouts.html 尽管Android提供了种类繁多的常用控件,但是有时你可能希望重用一些比较复杂的布局。如果要重用这些布局,可以使用< include/>标签与< merge/>标签,它们可将一个布局嵌入进另一个布局中。 可重用布局这项功能特别强大,它可以使你创建那些复杂的可重用布局。比方说,可以用来创建一个含有yes和no按钮的容器或者一个含有progressBar及一个文本框的容器。它还意味着程序可以对这些布局进行单独控制。所以,虽然说你可以通过自定义View的方式来实现更为复杂的UI组件,但是重用布局的方法更简便一些。 创建一个可重用的布局 如果你已经知道哪一个布局需要重用,那么就创建一个新的xml文件用来定义这个布局。下面就定义了一个ActionBar的布局文件,众所周知,ActionBar是会在每个Activity中统一出现的: <FrameLayout xmlns:android="http://schemas.android.com/apk/res/android" android:layout_width=”match_parent” android:layout_height="wrap_content" android:background="@color/titlebar_bg"> <ImageView android:layout_width="wrap_content" android:layout_height="wrap_content" android:src="@drawable/gafricalogo" /> </FrameLayout> 使用< include/>标签 在希望添加重用布局的布局内,添加< include/>标签。下面的例子就是将上面的布局加入到了当前的布局中: <LinearLayout xmlns:android="http://schemas.android.com/apk/res/android" android:orientation="vertical" android:layout_width=”match_parent” android:layout_height=”match_parent” android:background="@color/app_bg" android:gravity="center_horizontal"> <include layout="@layout/titlebar"/> <TextView android:layout_width=”match_parent” android:layout_height="wrap_content" android:text="@string/hello" android:padding="10dp" /> ... </LinearLayout> 你也可以重写布局的参数,但只仅限于以android:layout_*开头的布局参数。就像下面这样: <include android:id=”@+id/news_title” android:layout_width=”match_parent” android:layout_height=”match_parent” layout=”@layout/title”/> 如果你要重写< include>标签指定布局的布局属性,那么必须重写android:layout_height及android:layout_width这两个属性,以便使其它属性的作用生效。 使用< merge>标签 在将一个布局内嵌进另一个布局时,< merge>标签可以帮助消除冗余的View容器。举个例子,如果你的主布局是一个垂直的LinearLayout,在它的内部含有两个View,并且这两个View需要在多个布局中重用,那么重用这两个View的布局需要有一个root View。然而,使用单独的LinearLayout作为这个root View会导致在一个垂直的LinearLayout中又嵌了一个垂直的LinearLayout。其实这个内嵌的LinearLayout并不是我们真正想要的,此外它还会降低UI性能。 为了避免出现这种冗杂的View容器,你可以使用< merge>标签作为这两个View的root View: <merge xmlns:android="http://schemas.android.com/apk/res/android"> <Button android:layout_width="fill_parent" android:layout_height="wrap_content" android:text="@string/add"/> <Button android:layout_width="fill_parent" android:layout_height="wrap_content" android:text="@string/delete"/> </merge> 那么现在再使用这个布局的时候,系统会自动忽略< merge>标签,并会将两个Button View直接加入到布局< include/>标签所指定的位置。

资源下载

更多资源
Mario

Mario

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

腾讯云软件源

腾讯云软件源

为解决软件依赖安装时官方源访问速度慢的问题,腾讯云为一些软件搭建了缓存服务。您可以通过使用腾讯云软件源站来提升依赖包的安装速度。为了方便用户自由搭建服务架构,目前腾讯云软件源站支持公网访问和内网访问。

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部分的功能。

用户登录
用户注册