Python一键查找iOS项目中未使用的图片、音频、视频资源


Posted in Python onAugust 12, 2019

前言

在iOS项目开发的过程中,如果版本迭代开发的时间比较长,那么在很多版本开发以后或者说有多人开发参与以后,工程中难免有一些垃圾资源,未被使用却占据着api包的大小!

这里我通过Python脚本来查找项目中未被使用的图片、音频、视频资源,然后删除掉;以达到减小APP包大小的目的!

代码

先查找项目中所以的资源文件存到你数组里面

def searchAllResName(file_dir):
 global _resNameMap
 fs = os.listdir(file_dir)
 for dir in fs:
  tmp_path = os.path.join(file_dir, dir)
  if not os.path.isdir(tmp_path):
   if isResource(tmp_path) == True and '/Pods/' not in tmp_path and '.appiconset' not in tmp_path and '.launchimage' not in tmp_path:
    imageName = tmp_path.split('/')[-1].split('.')[0]
    _resNameMap[imageName] = tmp_path
    conLog.info_delRes('[FindRes OK] ' + tmp_path)
  elif os.path.isdir(tmp_path) and tmp_path.endswith('.imageset') and '/Pods/' not in tmp_path:
   imageName = tmp_path.split('/')[-1].split('.')[0]
   _resNameMap[imageName] = tmp_path
   conLog.info_delRes('[FindRes OK] ' + tmp_path)
  else:
   searchAllResName(tmp_path)

遍历查询项目的所以代码,查找工程中所引用的资源文件

# 查询项目的所以代码
def searchProjectCode(file_dir):
 global _projectPbxprojPath
 fs = os.listdir(file_dir)
 for dir in fs:
  tmp_path = os.path.join(file_dir, dir)
  if tmp_path.endswith('project.pbxproj'):
   _projectPbxprojPath = tmp_path
  if not os.path.isdir(tmp_path):
   if '/Pods/' not in tmp_path:
    try:
     findResNameAtFileLine(tmp_path)
     conLog.info_delRes('[ReadFileForRes OK] ' + tmp_path)
    except Exception as e:
     pass
     # conLog.error_delRes('[ReadFileForRes Fail] [' + str(e) + ']' + tmp_path)
  else:
   searchProjectCode(tmp_path)
# 查找工程中所引用的资源文件
def findResNameAtFileLine(tmp_path):
 global _resNameMap
 Ropen = open(tmp_path,'r')
 for line in Ropen:
  lineList = line.split('"')
  for item in lineList:
   # bar@2x barimg.png
   if item in _resNameMap or item.split('.')[0] in _resNameMap or item + '@1x' in _resNameMap or item + '@2x' in _resNameMap or item + '@3x' in _resNameMap:
    del _resNameMap[item]
 
 Ropen.close()

删除垃圾资源文件,这里垃圾资源文件删除分为两部分一部分是Assets.xcassets里面的,一部分是直接导入工程目录中的资源,如果是Assets.xcassets垃圾资源直接删除就行了,但是如果是直接导入到工程目录里面的资源,那就先删除project.pbxproj中的引用,再删除本地资源文件;

# 删除无用的资源文件
def delAllRubRes():
 global _resNameMap, _hadDelMap
 # .imageset类型的资源图片直接删除
 for resName in list(_resNameMap.keys()):
  tmp_path = _resNameMap[resName]
  if tmp_path.endswith('.imageset'):
   if os.path.exists(tmp_path) and os.path.isdir(tmp_path):
    try:
     # 已删除的元素
     _hadDelMap[resName] = tmp_path
     # 删除.imageset文件夹
     delImagesetFolder(tmp_path)
     # 字典移除
     del _resNameMap[resName]
     conLog.info_delRes('[DelRubRes OK] ' + tmp_path)
    except Exception as e:
     conLog.error_delRes('[DelRubRes Fail] [' + str(e) + ']' + tmp_path)
   else:
    conLog.error_delRes('[DelRubRes Fail] [not exists] ' + tmp_path)
 delResAtProjectPbxproj()
def delImagesetFolder(rootdir):
 filelist = []
 filelist = os.listdir(rootdir)
 for f in filelist:
  filepath = os.path.join( rootdir, f )
  if os.path.isfile(filepath):
   os.remove(filepath)
  elif os.path.isdir(filepath):
   shutil.rmtree(filepath,True)
 shutil.rmtree(rootdir,True)
# 直接导入到工程中的图片需要删除project.pbxproj中的引用,再移除本地文件
def delResAtProjectPbxproj():
 global _projectPbxprojPath, _resNameMap, _hadDelMap
 if _projectPbxprojPath != None:
  # 先把需要删除的资源名先保存一份
  _needDelResName = []
  file_data = ''
  Ropen = open(_projectPbxprojPath,'r')
  for line in Ropen:
   idAdd = True
   for resName in _resNameMap:
    if resName in line:
     idAdd = False
     if resName not in _needDelResName:
      _needDelResName.append(resName)
   if idAdd == True:
    file_data += line
  Ropen.close()
  Wopen = open(_projectPbxprojPath,'w')
  Wopen.write(file_data)
  Wopen.close()
  # 已经清理过project.pbxproj中的引用的资源文件,开始从_resNameMap中移除已被处理过的资源文件
  # 并删除本地的对应的资源文件
  for item in _needDelResName:
   tmp_path = _resNameMap[item]
   if os.path.exists(tmp_path) and not os.path.isdir(tmp_path):
    # 已删除的元素
    _hadDelMap[item] = tmp_path
    # 删除文件
    os.remove(tmp_path)
    # 字典移除
    del _resNameMap[item]
    conLog.info_delRes('[DelRubRes OK] ' + tmp_path)
   else:
    pass

总的调用函数

# 开始清理无用的垃圾资源文件
def startCleanRubRes(file_dir, ignoreList = []):
 global _resNameMap, _hadDelMap,_isCleaing
 if _isCleaing == True:
  return
 _isCleaing = True
 initData()
 conLog.info('-' * 30 + '开始清理资源文件' + '-' * 30)
 searchAllResName(file_dir)
 conLog.info_delRes('-' * 20 + '全部的资源文件列表' + '-' * 20)
 conLog.info_delRes(_resNameMap)
 for item in ignoreList:
  if item in list(_resNameMap.keys()):
   del _resNameMap[item]
 conLog.info_delRes('-' * 20 + '忽略删除的资源文件' + '-' * 20)
 conLog.info_delRes(ignoreList)
 searchProjectCode(file_dir)
 conLog.info_delRes('-' * 20 + '需要删除的资源文件' + '-' * 20)
 conLog.info_delRes(_resNameMap)
 delAllRubRes()
 conLog.info_delRes('-' * 20 + '删除成功的资源文件' + '-' * 20)
 conLog.info_delRes(_hadDelMap)
 conLog.info_delRes('-' * 20 + '删除失败的资源文件' + '-' * 20)
 conLog.info_delRes(_resNameMap)
 _isCleaing = False

软件

鉴于有些iOS开发程序员没有Python基础,这里做了一个图形化操作界面,欢迎大家下载使用!

下载地址:

https://gitee.com/zfj1128/ZFJ...

软件截图:

Python一键查找iOS项目中未使用的图片、音频、视频资源

总结

以上所述是小编给大家介绍的Python一键查找iOS项目中未使用的图片、音频、视频资,希望对大家有所帮助,如果大家有任何疑问请给我留言,小编会及时回复大家的。在此也非常感谢大家对三水点靠木网站的支持!
如果你觉得本文对你有帮助,欢迎转载,烦请注明出处,谢谢!

Python 相关文章推荐
Python 基础知识之字符串处理
Jan 06 Python
Python设计模式之门面模式简单示例
Jan 09 Python
python在非root权限下的安装方法
Jan 23 Python
Python Web编程之WSGI协议简介
Jul 18 Python
带你认识Django
Jan 15 Python
Python Process多进程实现过程
Oct 22 Python
Python lxml模块的基本使用方法分析
Dec 21 Python
在Pytorch中计算卷积方法的区别详解(conv2d的区别)
Jan 03 Python
Python能做什么
Jun 02 Python
浅谈Python描述数据结构之KMP篇
Sep 06 Python
python3中celery异步框架简单使用+守护进程方式启动
Jan 20 Python
Flask处理Web表单的实现方法
Jan 31 Python
django+echart数据动态显示的例子
Aug 12 #Python
Flask框架学习笔记之使用Flask实现表单开发详解
Aug 12 #Python
Flask框架学习笔记之表单基础介绍与表单提交方式
Aug 12 #Python
python内存管理机制原理详解
Aug 12 #Python
Flask框架学习笔记之路由和反向路由详解【图文与实例】
Aug 12 #Python
python实现图片压缩代码实例
Aug 12 #Python
django与vue的完美结合_实现前后端的分离开发之后在整合的方法
Aug 12 #Python
You might like
使用PHP接收POST数据,解析json数据
2013/06/28 PHP
PHP实现批量删除(封装)
2017/04/28 PHP
javascript 防止刷新,后退,关闭
2010/08/07 Javascript
php析构函数的具体用法小结
2014/03/11 Javascript
javascript中键盘事件用法实例分析
2015/01/30 Javascript
JS实现的表格操作类详解(添加,删除,排序,上移,下移)
2015/12/22 Javascript
Bootstrap菜单按钮及导航实例解析
2016/09/09 Javascript
PHP抓取HTTPS内容和错误处理的方法
2016/09/30 Javascript
vue中的scope使用详解
2017/10/29 Javascript
详解Vue.directive 自定义指令
2019/03/27 Javascript
微信小程序实现文件、图片上传功能
2020/08/18 Javascript
深入理解Vue keep-alive及实践总结
2019/08/21 Javascript
文章或博客自动生成章节目录索引(支持三级)的实现代码
2020/05/10 Javascript
vue页面跳转实现页面缓存操作
2020/07/22 Javascript
Vue看了就会的8个小技巧
2021/01/21 Vue.js
Python实现学校管理系统
2018/01/11 Python
python实现布隆过滤器及原理解析
2019/12/08 Python
python使用hdfs3模块对hdfs进行操作详解
2020/06/06 Python
Tensorflow中k.gradients()和tf.stop_gradient()用法说明
2020/06/10 Python
浅析CSS3 用text-overflow解决文字排版问题
2020/10/28 HTML / CSS
使用HTML和CSS实现的标签云效果(附demo)
2021/02/03 HTML / CSS
Solid & Striped官网:美国泳装品牌
2019/06/19 全球购物
SCHIESSER荷兰官方网站:德国内衣专家
2020/10/09 全球购物
物理专业大学生职业生涯规划书
2014/02/07 职场文书
社会学专业求职信
2014/07/17 职场文书
2014年学习厉行节约反对浪费思想汇报
2014/09/10 职场文书
乡镇干部个人对照检查材料思想汇报
2014/10/04 职场文书
乡镇三严三实学习心得体会
2014/10/13 职场文书
数学考试作弊检讨书300字
2015/02/16 职场文书
大学生求职自荐信
2015/03/24 职场文书
消费者投诉书范文
2015/07/02 职场文书
公司转让协议书
2016/03/19 职场文书
房屋转让协议书(标准范本)
2016/03/21 职场文书
2019年年中职场激励人心语录30条
2019/08/07 职场文书
浅析python中特殊文件和特殊函数
2022/02/24 Python
JS前端使用Canvas快速实现手势解锁特效
2022/09/23 Javascript