安装指定版本的CocoaPods

因为一些编译构建问题,我需要降级CocoaPods 过程如下: 卸载当前版本的CocoaPods sudo gem uninstall cocoapods 下载指定版本的CocoaPods,编译gem包 下载地址https://github.com/CocoaPods/CocoaPods/releases 将源码下载后解压,进入源码目录,编译gem包 gem build cocopods.gemspec 编译产物是 cocopods-版本号.gem 使用本地gem包安装CocoaPods sudo gem install cocopods-版本号.gem

October 31, 2019 · 1 min · holdsky

iOS xcodebuild自动构建常用命令

列出工作空间中的所有scheme xcodebuild -list -workspace abc.xcworkspace 输出 Information about workspace "abc": Schemes: abc AFNetworking FMDB GTMBase64 Minizip Pods-abc 列出项目的所有target及Configurations xcodebuild -list -project abc.xcodeproj 输出 Information about project "abc": Targets: abc Build Configurations: Debug Release If no build configuration is specified and -scheme is not passed then "Release" is used. Schemes: abc 编译指定的scheme或Target 指定scheme xcodebuild -workspace abc.xcworkspace -scheme test 或者 xcodebuild -project abc.xcodeproj -scheme test 此时默认编译 Release 版 ...

October 30, 2019 · 1 min · holdsky

Python JSONModel的实现思路

JSONModel,模型和JSON数据之间相互转换,或者模型和JSON数据的序列化、反序列化。 不同语言实现细节不一样,也并不是所有语言都可以实现。这里我参考Objective-C语言的JSONModel实现机制,设计了一种Python运行时JSON和Model的互转方案思路。 object类 用dir打印object >>> dir(object) ['__class__', '__delattr__', '__doc__', '__format__', '__getattribute__', '__hash__', '__init__', '__new__', '__reduce__', '__reduce_ex__', '__repr__', '__setattr__', '__sizeof__', '__str__', '__subclasshook__'] 挨个找,看到两个方法 __setattr__ 和 __getattribute__,看名字也大概知道用途,基本意思就是可以通过 __setattr__ 和 __getattribute__ 访问object实例的属性值。 具体可参考https://www.cnblogs.com/elie/p/6685429.html __setattr__ 如果类自定义了 __setattr__ 方法,当通过实例获取属性尝试赋值时,就会调用 __setattr__。常规的对实例属性赋值,被赋值的属性和值会存入实例属性字典 __dict__ 中;如下类自定义了 __setattr__,对实例属性的赋值就会调用它。类定义中的self.attr也同样,所以在 __setattr__ 下还有self.attr的赋值操作就会出现无线递归的调用 __setattr__ 的情况。自己实现 __setattr__ 有很大风险,一般情况都还是继承object类的 __setattr__ 方法。 __getattribute__ 实例instance通过instance.name访问属性name, __getattribute__ 方法一直会被调用,无论属性name是否追溯到。如果类还定义了 __getattr__ 方法,除非通过 __getattribute__ 显式的调用它,或者 __getattribute__ 方法出现AttributeError错误,否则 __getattr__ 方法不会被调用了。如果在 __getattribute__(self, attr) 方法下存在通过self.attr访问属性,会出现无限递归错误。 步骤 只讨论最小场景(当然可以自行扩展) json -> model 这里假设json是一个字典,且没有嵌套情况。 并且假设应知道model的类名,一个字典对应一个model。 遍历json所有key ,然后按照key名称给model的属性赋值。 示意代码 dict = json数据 model=类的实例 for (key,value) in dict.items(): model.__setattr__(key,value) model -> json 这里假设model的所有属性都能转化为对应的json数据,且没有嵌套。 这里,还需要借助 __dict__ 函数 ...

October 28, 2019 · 1 min · holdsky

ssh登陆慢,经常超时,卡在pledge: network之后

ssh登陆,添加 -v 参数,可以打印详细的登陆过程 ssh -v 主机配置 例如 ssh -v -T -D 62403 -o ConnectTimeout=15 我的主机配置 但是经常超时,卡在了 debug1:pledge: network 主要原因是大量的爆破扫描,因此导致btmp这个文件巨大。 解决办法 echo "" > /var/log/btmp 或者 直接删除这个日志文件 重启sshd服务 参考: https://blog.csdn.net/Liv2005/article/details/84258580

October 28, 2019 · 1 min · holdsky

wxGlade : 生成的EVT_CLOSE关闭事件代码,运行崩溃

我用wxGlade生成Python的UI代码,但添加监听EVT_CLOSE事件代码时,运行崩溃 Traceback (most recent call last): File "/Users/zxs.zl/Desktop/Yan/github/XcodeBuildPyUI/zlBuild/app.py", line 16, in OnInit self.frame = mainFrame(None, wx.ID_ANY, "") File "/Users/zxs.zl/Desktop/Yan/github/XcodeBuildPyUI/zlBuild/mainFrame.py", line 38, in __init__ self.Bind(wx.EVT_CLOSE, self.onWindowClose, self.frame) AttributeError: 'mainFrame' object has no attribute 'frame' 生成的代码部分: class mainFrame(wx.Frame): def __init__(self, *args, **kwds): # begin wxGlade: mainFrame.__init__ 部分代码如下 self.Bind(wx.EVT_BUTTON, self.onClickBuildLibButton, self.buildLibButton) self.Bind(wx.EVT_CLOSE, self.onWindowClose, self.frame) # end wxGlade 将生成的代码 self.frame 改为 self,运行正常 # self.Bind(wx.EVT_CLOSE, self.onWindowClose, self.frame) self.Bind(wx.EVT_CLOSE, self.onWindowClose, self)

October 23, 2019 · 1 min · holdsky

macOS Catalina 10.15 : xxx向访问"桌面"文件夹

升级到macOS Catalina 10.15后,打开一些应用程序,会弹出 xxx向访问"桌面"文件夹 对话框。 如果点击 不允许,有些应用程序会触发崩溃退出,但是再次打开这些应用程序,系统不会重新弹出上门的对话框,应用程序也就再次退出了。 解决办法是在 系统偏好设置 -> 安全和隐私 -> 文件和文件夹 找到对应的应用程序,设置 允许 权限就好了。

October 22, 2019 · 1 min · holdsky

标记Objective-C的类不能被继承

在做swift和OC混编时,学到的. 使用 attribute 指令,将Objective-C的类标记为objc_subclassing_restricted。 如 //标记ClassA不能被继承 __attribute__((objc_subclassing_restricted)) @interface ClassA : NSObject @end @implementation ClassA @end //下面代码会报错 //error: Cannot subclass a class that was declared with the 'objc_subclassing_restricted' attribute @interface ClassB: ClassA @end @implementation ClassB @end

October 18, 2019 · 1 min · holdsky

iOS13适配:UIWindow窗口和导航控制器

@ 这次iOS13的发布,其改动步子有点大了,尤其是是其多场景窗口(多任务)已经颠覆了老应用的设计基础了—-数据的协同共享处理机制(本文不谈,哈哈) 这里记录下一些界面层面的适配体会: 如果是 Xcode 10 及以下创建的老项目,用 Xcode 11 打开,老项目基本能正常运行。但是如果用 Xcode 11 创建新项目,还按照老项目思路写代码就会有坑了。 用 Xcode 11 创建一个 Single View App 项目,会多生成一些文件和代码 多了SceneDelegate代理 Info.plist里面多了Application Scene Manifest配置 多出来的这些文件和代码,影响最直观的是多场景窗口和导航控制器。 适配方案——不支持多场景窗口 这种适配方案最简单。 将多出来的文件和代码删除就好了 删除SceneDelegate代理文件 (可选) 删除 Info.plist里面的Application Scene Manifest配置(一定要删除) 删除 AppDelegate代理的两个方法: application:configurationForConnectingSceneSession:options: application: didDiscardSceneSessions: 这两个方法一定要删除,否则使用纯代码创建的 Window 和导航控制器 UINavigationController 不会生效。 适配方案——支持多场景窗口 先说我遇到的一些现象。 尽管我不会为每个应用自定义窗口和导航,但我我依然会使用纯代码创建 UIWindow 和 UINavigationController,具体如下 //AppDelegate - (BOOL)application:(UIApplication *)application didFinishLaunchingWithOptions:(NSDictionary *)launchOptions { //在Xcode11创建的项目中,需要自行给AppDelegate添加属性window //自定义Window self.window = [[UIWindow alloc] initWithFrame:[UIScreen mainScreen].bounds]; //自定义导航控制器 UINavigationController *rootNavgationController = [[UINavigationController alloc] initWithRootViewController:[ViewController new]]; //导航控制是rootViewController self.window.rootViewController = rootNavgationController; //现实Window [self.window makeKeyAndVisible]; return YES; } Xcode 11 创建的项目中,写入上述代码运行App,结果发现这部分代码虽然执行了,但是通过UIViewController的 self.navigationController 获取的导航竟然是 nil。 从现象反推过程,既然代码执行了,那么很大可能是 self.window 没有显示在屏幕上。 查看iOS13下 UIWindow 的定义,有这么一条 ...

October 17, 2019 · 2 min · holdsky

create-react-app :不产生source-map来缩减打包文件体积

用create-react-app 脚手架创建的react项目,使用 npm run build 打包后,默认会产生 source-map 文件,通常项目上线后这种文件是不必要的。 现在需要配置以关闭这种文件的产生。 打开项目的 package.json 文件,找到下面类似的配置 "scripts": { "analyze": "source-map-explorer 'build/static/js/*.js'", "start": "react-scripts start", "build": "react-scripts build", "test": "react-scripts test", "eject": "react-scripts eject" }, 可以看到 build 命令执行的脚本是 react-scripts build,然后打开 node_modules/react-scripts/config/webpack.config.js 文件。 一般情况下,定位到这,基本就知道了怎么关闭 source-map 文件产生–搜索 shouldUseSourceMap,将其置为false就行了。 如果仔细查看 shouldUseSourceMap 定义 const shouldUseSourceMap = process.env.GENERATE_SOURCEMAP !== 'false'; 会发现shouldUseSourceMap和 process.env.GENERATE_SOURCEMAP 环境变量有关,那么在不修改 webpack.config.js 文件的情况,其实还可以修改环境变量。( 环境变量修改参考 https://139.155.43.7/2019/10/15/create-react-app-%e8%87%aa%e5%ae%9a%e4%b9%89%e7%8e%af%e5%a2%83%e5%8f%98%e9%87%8f/ ) 在项目目录下创建.env文件,添加内容 GENERATE_SOURCEMAP=false 然后重新执行 npm run build,这时应不会产生 source-map 文件

October 15, 2019 · 1 min · holdsky

create-react-app : 自定义环境变量

create-react-app是一款非常好用的react项目脚手架,其创建的react项目除了可以访问默认的环境变量,还可以自定义环境变量,只要在项目目录下创建 .env 文件,然后直接写入环境变量就可以了。 具体如下: 1、创建.env文件 在react项目目录下创建 .env 文件。 2、写入环境变量,例如 ABCD=1 3、访问环境变量 对于默认定义好的环境变量,使用 process.env.默认环境变量名 访问 对于自定义环境变量,需要添加 REACT_ 前缀,即使用 process.env.REACT_自定义环境变量名 访问 例如 render() { if (process.env.REACT_ABCD !== 0 ) { '示例' } return ( <div> <span> 默认环境变量示例 {process.env.NODE_ENV </span> <span> 自定义环境变量示例 {process.env.REACT_ABCD </span> </div> ); } 参考 : https://create-react-app.dev/docs/adding-custom-environment-variables

October 15, 2019 · 1 min · holdsky