android 6.0动态权限写在第一个activity中就行了吗

Posted

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了android 6.0动态权限写在第一个activity中就行了吗相关的知识,希望对你有一定的参考价值。

参考技术A

不是的,要在申请权限的过程中。

申请权限步骤

    注意,如果你将targetSdkVersion设置为>=23,则必须按照android谷歌的要求,动态的申请权限,如果你暂时不打算支持动态权限申请,则targetSdkVersion最大只能设置为22.

    在AndroidManifest.xml中申请你需要的权限,包括普通权限和需要申请的特殊权限。

    开始申请权限,此处分为3步:检查是否由此权限checkSelfPermission(),如果已经开启,则直接做你想做的。如果未开启,则判断是否需要向用户解释为何申请权限shouldShowRequestPermissionRationale。如果需要(即返回true),则可以弹出对话框提示用户申请权限原因,用户确认后申请权限requestPermissions(),如果不需要(即返回false),则直接申请权限requestPermissions。

参考技术B 不是。在你需要请求权限时。 参考技术C 运行时权限处理
Android6.0系统默认为targetSdkVersion小于23的应用默认授予了所申请的所有权限,所以如果你以前的APP设置的targetSdkVersion低于23,在运行时也不会崩溃,但这也只是一个临时的救急策略,用户还是可以在设置中取消授予的权限。
声明目标SDK版本
我们需要在build.gradle中声明targetSdkVersion为23

android
compileSdkVersion 23
buildToolsVersion "23.0.1"

defaultConfig
applicationId "com.yourcomany.app
minSdkVersion 18
targetSdkVersion 23
versionCode 1
versionName "1.0"

buildTypes release minifyEnabled false proguardFiles getDefaultProguardFile('proguard-android.txt'), 'proguard-rules.pro'

检查并申请权限
我们需要在用到权限的地方,每次都检查是否APP已经拥有权限,比如我们有一个下载功能,需要写SD卡的权限,我们在写入之前检查是否有WRITE_EXTERNAL_STORAGE权限,没有则申请权限

if (ContextCompat.checkSelfPermission(this, Manifest.permission.WRITE_EXTERNAL_STORAGE)
!= PackageManager.PERMISSION_GRANTED)
//申请WRITE_EXTERNAL_STORAGE权限
ActivityCompat.requestPermissions(this, new String[]Manifest.permission.WRITE_EXTERNAL_STORAGE,
WRITE_EXTERNAL_STORAGE_REQUEST_CODE);


请求权限后,系统会弹出请求权限的Dialog
用户选择允许或需要后,会回调onRequestPermissionsResult方法, 该方法类似于onActivityResult
@Override
public void onRequestPermissionsResult(int requestCode, String[] permissions, int[] grantResults)
super.onRequestPermissionsResult(requestCode, permissions, grantResults);
doNext(requestCode,grantResults);


我们接着需要根据requestCode和grantResults(授权结果)做相应的后续处理
private void doNext(int requestCode, int[] grantResults)
if (requestCode == WRITE_EXTERNAL_STORAGE_REQUEST_CODE)
if (grantResults[0] == PackageManager.PERMISSION_GRANTED)
// Permission Granted
else
// Permission Denied




Fragment中运行时权限的特殊处理
在Fragment中申请权限,不要使用ActivityCompat.requestPermissions, 直接使用Fragment的requestPermissions方法,否则会回调到Activity的 onRequestPermissionsResult
如果在Fragment中嵌套Fragment,在子Fragment中使用requestPermissions方 法,onRequestPermissionsResult不会回调回来,建议使用 getParentFragment().requestPermissions方法,这个方法会回调到父Fragment中的onRequestPermissionsResult,加入以下代码可以把回调透传到子Fragment
@Override
public void onRequestPermissionsResult(int requestCode, String[] permissions, int[] grantResults)
super.onRequestPermissionsResult(requestCode, permissions, grantResults);
List<Fragment> fragments = getChildFragmentManager().getFragments();
if (fragments != null)
for (Fragment fragment : fragments)
if (fragment != null)
fragment.onRequestPermissionsResult(requestCode,permissions,grantResults);





相关开源项目
PermissionsDispatcher
使用标注的方式,动态生成类处理运行时权限,目前还不支持嵌套Fragment。
RxPermissions
基于RxJava的运行时权限检测框架
Grant
简化运行时权限的处理,比较灵活
android-RuntimePermissions
Google官方的例子
附录
以下权限只需要在AndroidManifest.xml中声明即可使用
android.permission.ACCESS_LOCATION_EXTRA_COMMANDS
android.permission.ACCESS_NETWORK_STATE
android.permission.ACCESS_NOTIFICATION_POLICY
android.permission.ACCESS_WIFI_STATE
android.permission.ACCESS_WIMAX_STATE
android.permission.BLUETOOTH
android.permission.BLUETOOTH_ADMIN
android.permission.BROADCAST_STICKY
android.permission.CHANGE_NETWORK_STATE
android.permission.CHANGE_WIFI_MULTICAST_STATE
android.permission.CHANGE_WIFI_STATE
android.permission.CHANGE_WIMAX_STATE
android.permission.DISABLE_KEYGUARD
android.permission.EXPAND_STATUS_BAR
android.permission.FLASHLIGHT
android.permission.GET_ACCOUNTS
android.permission.GET_PACKAGE_SIZE
android.permission.INTERNET
android.permission.KILL_BACKGROUND_PROCESSES
android.permission.MODIFY_AUDIO_SETTINGS
android.permission.NFC
android.permission.READ_SYNC_SETTINGS
android.permission.READ_SYNC_STATS
android.permission.RECEIVE_BOOT_COMPLETED
android.permission.REORDER_TASKS
android.permission.REQUEST_INSTALL_PACKAGES
android.permission.SET_TIME_ZONE
android.permission.SET_WALLPAPER
android.permission.SET_WALLPAPER_HINTS
android.permission.SUBSCRIBED_FEEDS_READ
android.permission.TRANSMIT_IR
android.permission.USE_FINGERPRINT
android.permission.VIBRATE
android.permission.WAKE_LOCK
android.permission.WRITE_SYNC_SETTINGS
com.android.alarm.permission.SET_ALARM
com.android.launcher.permission.INSTALL_SHORTCUT
com.android.launcher.permission.UNINSTALL_SHORTCUT本回答被提问者采纳

Android逆向-Android基础逆向(2-2)

[toc]

#0x00 前言
##不知所以然,请看
Android逆向-Android基础逆向(1)
Android逆向-Android基础逆向(2)
##以及java系列:
Android逆向-java代码基础(1)
Android逆向-java代码基础(2)
Android逆向-java代码基础(3)
Android逆向-java代码基础(4)
Android逆向-java代码基础(5)
Android逆向-java代码基础(6)
Android逆向-java代码基础(7)
Android逆向-java代码基础(8)
由于之前的Android逆向-Android基础逆向(2)的伪加密部分篇幅太长,导致其他内容没有完成,所以才有了这里的Android逆向-Android基础逆向(2-2)。希望可以完成计划中的内容。
##学习内容
(1)APK文件伪加密√
(2)资源文件防反编译
(3)apk打包流程
(4)apk反编译流程
(5)apk回编译流程、
#0x01 资源文件防反编译
之前说过可以通过更改第四个字段来进行防止一定程度的反编译。那么除了这种伪加密的方式,还有什么方式可以防止这种伪加密的出现呢。
来看看资源文件是如何防止反编译的。
自然我们需要研究一下xml文件的格式。四哥在2016年已经分析过了,不过那是人家分析的,只看别人分析的不能进行更深入的学习。纸上得来终觉浅,绝知此事要躬行。so,就有了这篇。
##1.第一个模块
技术分享图片
这里对应使用一个实例分析,就用Android逆向-Android基础逆向(1)中的简单的apk来分析吧。
###1.1 Magic Number
技术分享图片
这里魔数是00 08 00 03,这个是一个固定的值。
###1.2File Size
这个就是用来确认文件大小的。
技术分享图片
这里是00 00 07 90 ,也就是1970个bytes。
###1.3用python实现分析
四哥用java写的,我就献丑写个python的,还在学习python的过程中,有什么错误或者做的不好的地方,还请见谅。
这个是实现这个模块的代码。但是感觉自己写的好繁琐,等一会儿适当修改一下。
2018年1月27日11:57:35,忙别的事情去了。

def fenxi(filename):
    try:
        f=open(filename,‘rb‘)
        print ‘start--------‘
        i=0
        p1=""
        p2=""
        p3=""
        p4=""
        p=""
        while True:
            t=f.read(1)
            t1=t.encode(‘hex‘)
            if i==0:
                p1=t1
            if i==1:
                p2=t1
            if i==2:
                p3=t1
            if i==3:
                p4=t1
            i=i+1
            if i<4:
                p=p+" "
            if i==4:
                break
            pass
        p=p4+" "+p3+" "+p2+" "+p1   
        print "Magic Number:",p
        i=0
        p1=""
        p2=""
        p3=""
        p4=""
        p=""
        while True:
            t=f.read(1)
            t1=t.encode(‘hex‘)
            if i==0:
                p1=t1
            if i==1:
                p2=t1
            if i==2:
                p3=t1
            if i==3:
                p4=t1
            i=i+1
            if i<4:
                p=p+" "
            if i==4:
                break
            pass
        p=p4+" "+p3+" "+p2+" "+p1   
        print "FileSize:",p
    except IOError:
        print "This is bad for input ‘",name,"‘." 
        print "You can enter -h for help." 

2.第二个模块

技术分享图片
###1.Chunk Type
String Chunk 的标识符,默认是00 08 00 03
技术分享图片

2.Chunk Size

String Chunk的大小。
技术分享图片
技术分享图片

3.String Count

字符串的个数。
技术分享图片

4.Style Count

样式的个数
技术分享图片
技术分享图片

5.Unknow

技术分享图片
技术分享图片

6.String Pool Offset

首部偏移量,也就是String Chunk的位置。
技术分享图片
技术分享图片

7.Style Pool Offset

样式偏移,但是因为样式没有。所以这里全部为0

8.String Offsets

这个是字符串偏移,大小就是String count*4个bytes
技术分享图片

9.常量池

这个就是最主要的地方了。不过中间有一个0的空字符串。需要注意,然后使用一个循环就可以简单的分析出来了。
这里帖出代码部分。

while True:
            t1=f.read(1)
            t2=f.read(1)
            tf1=t1.encode(‘hex‘)
            tf2=t2.encode(‘hex‘)
            p1=tf2+tf1
            ph=int(p1, 16)
            p3=""
            i=0
            while True:
                t=f.read(1)
                t1=t.encode(‘hex‘)
                p=int(t1, 16)
                p3=p3+chr(p)
                t=f.read(1)
                i=i+1
                if i==ph:
                    break
                pass
            print "first string:",p3
            t=f.read(2)
            if l==12:
                t=f.read(4)
            l=l+1
            if l==x-1:

                break

运行结果展示:
技术分享图片
技术分享图片

3.第三个模块 Resourceld Chunk

技术分享图片
这个Chunk主要是存放的是AndroidManifest中用到的系统属性值对应的资源Id

3.1 Chunk Type

和其他Chunk一样,都有特征值,Resourceld Chunk的特征值是:0x00080108
技术分享图片

3.2 Chunk Size

Size大小没有什么好解释的。
技术分享图片

3.3Resourcelds

技术分享图片
技术分享图片
这里可以根据id在frameworks\base\core\res\res\values\public.xml中查找到相对应的string。
一下是简单的代码模块:

a=p/4-2
        i1=0
        while True:
            i=0
            p1=""
            p2=""
            p3=""
            p4=""
            p=""
            while True:
                t=f.read(1)
                t1=t.encode(‘hex‘)
                if i==0:
                    p1=t1
                if i==1:
                    p2=t1
                if i==2:
                    p3=t1
                if i==3:
                    p4=t1
                i=i+1
                if i==4:
                    break
                pass
            p=p4+p3+p2+p1   
            p5=p4+" "+p3+" "+p2+" "+p1
            p=int(p, 16)
            print "123id:",p,"bytes","hex:",p5
            i1=i1+1
            if i1==a:
                break 

4.第四个模块

技术分享图片
这个Chunk主要包含一个AndroidManifest文件中的命令空间的内容

4.1 Chunk Type

特征码,这里不强调了。 特征码是00 10 01 00。
技术分享图片

4.2 Chunk Size

Chunk的大小。
技术分享图片

4.3 Line Number

在AndroidManifest文件中的行号
技术分享图片

4.4Unknown

未知区域,一般是ffff
技术分享图片

4.5 Prefix

命名空间的前缀
技术分享图片

4.6Uri

命名空间的Urk
技术分享图片

5.第五个模块

这个模块主要是为了存放标签信息
这里要啰嗦了。第五个模块要写完的时候,突然鼠标的返回键被按到了。我都在想是不是应该在本地写了,而不是在云端写,太感人了这个。伤心。准备偷懒了。
技术分享图片

5.1 Chunk Type

标志字段,固定字符。
00 10 01 02

5.2 Chunk Size

Chunk 大小

5.3 Line Number

行数,和上一个段一样

5.4 Unknown

位置区域

5.5Namespace Uri

标签用的uri,但是也有可能是返回 ff ff ff ff。
代码实现:

i=0
    p1=""
    p2=""
    p3=""
    p4=""
    p=""
    while True:
        t=f.read(1)
        t1=t.encode(‘hex‘)
        if i==0:
            p1=t1
        if i==1:
            p2=t1
        if i==2:
            p3=t1
        if i==3:
            p4=t1
        i=i+1
        if i==4:
            break
        pass
    p=p4+p3+p2+p1   
    p=int(p, 16)
    try :
        print "Namespace Uri:",list[p]      
    except IndexError:
        print "Namespace Uri is nothing"

技术分享图片

5.6 name

标签名称字段
技术分享图片

5.7 flags字段

标识是开始flags还是结束flags
技术分享图片

5.8 Attribute Count

包含属性的个数
技术分享图片

5.9 Class Attribute

标签包含的类属性
技术分享图片

5.10Attributes Attribute

属性内容。包括NamespaceUri,Name,ValueString,type,Data,这五个字段。
技术分享图片

6.第六个模块

技术分享图片
这个和第五个块一样。
技术分享图片

7.第七个模块

因为是和之前的模块一样这里就不做解释了
技术分享图片

收获

##python
1.python右移的方式
2.python格式转换
3.对二进制模块分析
4.这个是最大的收货,得到了一个xml文件分析工具。
5.github地址:xml.py文件分析

结束语

感觉这里需要的内容很多,就得要分成很多小块来说。为什么这里要写关于xml的分析呢,因为加固的目的就是为了防止反编译。那么我们可以针对反编译软件进行针对化加固,在下一个小块将会详细讲解。

以上是关于android 6.0动态权限写在第一个activity中就行了吗的主要内容,如果未能解决你的问题,请参考以下文章

android6.0以上权限动态申请

在Android 6.0 设备上动态获取权限

Android 6.0以上动态请求权限的工具类

Android APP启动页面动态加载全部权限

Android 6.0: 动态权限管理的解决方案

android 6.0之后动态获取权限