2

PaaS服务从Heroku迁移到fly.io小计

 1 year ago
source link: https://www.leavesongs.com/SOFT/paas-service-from-heroku-to-fly-io.html
Go to the source link to view the article. You can view the picture content, updated content and better typesetting reading experience. If the link is broken, please click the button below to view the snapshot at that time.
neoserver,ios ssh client

今年8月得知了Heroku将要在今年11月彻底下线免费服务,我只有少量服务放在Heroku上,所以没有太在意,直到10月感觉到不得不开始做迁移相关的工作了,于是开始着手准备,并有了这篇文章。

这篇文章纯属是事后记录的一些流水账,可能缺少截图和代码片段,全当是作为一个故事看,可能不具备参考性。

为什么选择PaaS服务

从很久以前开始接触“虚拟主机”这个行业开始,我经历了虚拟主机、VPS、云主机、PaaS、容器等时代——从最早我不需要有任何运维成本的虚拟主机,需要完全自己运维的VPS主机,又回归到不太需要自己运维的PaaS服务,就像兜了一个圈。

PaaS全名平台即服务(Platform as a Service),意思是云平台提供了一套部署“框架”,可以将你编写的代码通过它的方式一键部署在云上,并且给你提供网络、存储、日志等常用的服务,解决了开发人员的运维问题,我们只需要写好代码提交,后期所有的自动化部署、发布、运维、扩展、备份等逻辑都可以让云平台帮我完成。

其实容器与k8s的思想也是脱胎于此,现在看来,容器就是将这样的需求标准化成为了一套规范。相对来说,容器的可定制化程度更高,也算是PaaS服务在2015年以后的逐步进化。

其实我一直认为,早期的虚拟主机发展到后面就是PaaS,PaaS继续发展就是现在的容器即服务(CaaS)。所以,本文所谓的PaaS的概念,并不局限在一两个名词之中,而是泛指这一类基于某种特定的框架来自动化部署的平台。

早期著名的PaaS平台有谷歌的GAE、新浪的SAE、Heroku等,PaaS这个概念能很快打入开发群体之中的关键原因之一是免费。在2015年左右,正是GAE、SAE等平台最火的时候, 我记得曾经有不少教程教大家如何部署应用到GAE,甚至有的翻墙工具也直接部署在GAE上。

发展到今天,新浪的SAE早已半入土,谷歌Cloud SAE因为高昂的学习成本与产品设计,也被我抛弃了。

我记得之前部署过服务在GAE上,但因为用错了环境导致没有满足Free Tier资格仍然被扣费。其后台管理与付费逻辑十分难懂,在账单出来前你很难知道自己在用的服务价格,我开始抵触这类收费标准不明确的后付费产品,就怕哪天早上起床突然发现房子被人收走了。

image.png

对于个人开发者来说,相对比较友好的平台是Heroku,它提供了每个月550到1000小时的免费运行时间,同时还有免费的PostgreSQL和Redis服务,搭配我常用的Django环境是绝配。

对于一个全时间段运行的应用来说,一个月需要跑24 x 30 = 720个小时,免费额度完全没有问题。但免费套餐最大的缺点就是在不活跃30分钟后会被自动停止,等下次有人请求的时候会再重启启动,这会导致这个请求消耗更多时间。

免费套餐非常适合部署一些演示站点、不活跃的站点等,我在2018年做Code-Breaking的时候将官网部署在了Heroku:

image-20221016013617076.png

这一部署就是4年,直到2022年10月我将其迁移到fly.io,它都静静地运行在那里,无需我任何的管理,也没有任何错误。这确实满足了我当时选择Heroku的所有需求——对于一个短期内使用的临时性站点,我要做的就是尽可能减少后期的管理成本,只要能一直运行就行。

想一下,这可能是存活时间最久的CTF站点之一了。

当然,我前文也说了,Heroku在8月宣布要下线免费套餐。这可能是PaaS服务最大的风险,来自于平台政策的变化,而Heroku最便宜的套餐也是一小时0.01美刀,合计7刀一个月,还不算PostgreSQL和Redis数据库的费用。

为什么选择fly.io

巧的是前段时间看到一个推特博文介绍了一个平台叫fly.io:

image.png

我了解了一下fly,这是一家来自美国的初创公司。其提供的免费服务如下:

  • 3个1核256MB内存的环境,用于运行应用
  • 3G的Volume,可以用于部署数据库等
  • 160GB每月的流量

其实即使不考虑免费套餐,其定价也比较亲民,不用担心免费额度用超了以后的价格问题:

image.png

于是我就决定将code-breaking迁移到fly.io上,作为Heroku的替代。

迁移代码到fly.io

fly.io由于诞生在容器时代,所以本身就是基于容器的,有额外学习成本。

先安装其客户端flyctl并进行认证,然后来到code-breaking项目根目录,执行flyctl launch。此时,flyctl会根据当前项目的结构识别出待部署应用类型,比如我的是Django:

image.png

按照指引完成配置,此时会创建Web应用和一个数据库应用(PostgreSQL),并生成两个文件:

  • Dockerfile
  • fly.toml

其中Dockerfile就是将会运行这个应用的镜像模板,里面已经简单帮我实现了大部分部署Django的代码,在基础上稍稍改动就可以直接使用。

fly.toml是fly.io的配置文件,没有特殊的需求的情况下不用修改。

然后我执行flyctl deploy部署。默认情况下,flyctl会将当前项目发送到云端,在云端的一个虚拟机里进行镜像编译部署。不过,在成功编译几次后我就无法使用远程编译了,执行flyctl deploy无法连接上虚拟机,会出现“Failed to start remote builder heartbeat”的错误,使用flyctl deploy --local-only改成本地编译可以解决这个问题。

部署结束后,fly.io会提供一个二级域名,通过code-breaking.fly.dev即可访问刚才部署的应用。

当然,这只是第一步工作,后面我还需要解决域名和持久化数据的问题:

  • 静态资源的部署
  • 数据库的迁移
  • 域名与证书绑定

静态资源的部署

初始化时生成的fly.toml文件中有关于volume的配置:

[[statics]]
  guest_path = "/app/public"
  url_prefix = "/static/"

意思就是/app/public这个目录下的文件将会作为静态资源,在Web中的URL前缀是/static/。所以,我只需修改Django配置即可:

STATIC_URL = '/static/'
STATIC_ROOT = '/app/public'

数据库的迁移

数据库需要从Heroku迁移到fly.io,我选择使用Navicat手工来做这件事,首先就是连接Heroku和fly.io的PostgreSQL数据库。

Heroku的数据库是对公网开放的,我们只需要拿到它的地址与账号密码,执行如下命令:

heroku pg:credentials -a [appname]

此时会输出一个数据库连接URL,其中会包含地址、端口和账号密码。

而fly.io的数据库是一个内网地址,我需要使用flyctl自带的proxy功能将其转发到本地再进行连接。在创建数据库的时候flyctl会打印其内网地址和账号密码,然后通过proxy命令来将端口转发出来:

flyctl proxy 5432:5432 code-breaking-db.internal -a code-breaking-db

再使用Navicat直接连接本地的5432端口即可,后续数据迁移操作,直接在Navicat里进行。

域名与证书绑定

默认情况下,部署完成的应用将会分配一个二级域名,但我明显需要绑定自己的域名。方法是来到官网后台Certificates页面,点击“Add certificate”,此时它会要求你添加三个解析:

image.png

其实这个地方的逻辑非常不清晰,明明是绑定域名,但这个功能却叫“Certificates”,以至于让我在这一块浪费了很多时间。

fly.io给我们的IP实际上是一个共享IP,是通过HTTPS证书中的hostname或HTTP头里的Host来确认访问者要访问的主机,我猜这也是为什么这个功能叫“Certificates”的原因,在不添加证书的情况下我们无法正确通过自己的域名访问到应用。

所以,来到Cloudflare中,添加好这几个解析记录,其中_acme-challenge最好是DNS Only:

image.png

然后回到“Certificates”页面点击check again,验证成功后即绑定好了域名。

此时我们再通过Code-Breaking就正常访问到了Code-Breaking的官网,全部的部署完成。

体验与感受

完整部署下来,可以明显感觉到fly.io的成熟程度远远落后于heroku,其flyctl客户端仍然存在一些Bug,文档也不齐全。虽说我轻描淡写地描述了我整个部署的过程,但实际上其中踩坑无数,甚至远程编译的Bug在触发后就再也没解决过,官方社区也多是问题鲜有靠谱答案。

就功能上来看,fly.io也比较少,只能说刚好满足我现在的需要。

其优点就是具有免费的额度,价格也便宜,对于个人开发者来说也很友好。而且相比于heroku来说,fly.io仅是一个初创公司,仍具有很大的想象力,相信现有的这些不足也会慢慢解决与完善。

最后,在写文的时候看到fly.io的招聘页面,这家公司Base在芝加哥但大部分员工属于远程办公。我在招聘列表里也看到了安全工程师的岗位:https://fly.io/jobs/security-engineer/,$120k to $200k USD 年薪对于远程工作来讲还是很有吸引力的,有兴趣的同学可以关注一下。


About Joyk


Aggregate valuable and interesting links.
Joyk means Joy of geeK