Questions and discussions about using the Shopify CLI and Shopify-built libraries.
Hi everyone
I am a bit of a newbie to the world of Shopify Remix, but I am really loving the stack. 🙂
I want to use node-cron in my Remix App.
I am using fly.io for my hosting requirements:
fly deploy
The default container script Dockerfile, does not pre-install cron.
But the documentation suggests, using a library called supercronic:
https://fly.io/docs/app-guides/supercronic/
The part I don’t get, is the bit about processes in fly.toml?
[processes]
# The command below is used to launch a Rails server; be sure to replace with the command you're using to launch your server.
web = "bin/rails fly:server"cron = "supercronic /app/crontab"
# Make sure there's only one `processes` entry under `[[services]]`
[[services]]
processes = ["web"]
I feel that we should remove the services section, altogether, and the web part of the processes section. I am pretty sure these don’t apply, if you are running a Node based application, like a Remix App?
My current fly.toml does not have a services or a processes section.
I presume Remix Apps don’t require Rails? They run off NodeJs, which is pre installed from the Dockerfile script:
FROM node:18-alpine
EXPOSE 3000
WORKDIR /app
COPY . .
RUN npm install
RUN npm run build
# You'll probably want to remove this in production, it's here to make it easier to test things!
RUN rm prisma/dev.sqlite
RUN npx prisma migrate dev --name init
CMD ["npm", "run", "start"]
Can anyone explain the best way to install cron, using the default Remix fly.io container?
Maybe I can just add this to my Dockerfile:
RUN apt-get update
RUN apt-get install -y cron
Does anyone know where I should add these two commands, in the Dockerfile?
Update:
I can now show you, what the Dockerfile, should look like:
FROM node:18-alpine
EXPOSE 3000
WORKDIR /app
COPY . .
RUN npm install
RUN npm run build
# You'll probably want to remove this in production, it's here to make it easier to test things!
RUN rm prisma/dev.sqlite
RUN npx prisma migrate dev --name init
# Install prerequisites
RUN add --update curl
# Latest releases available at https://github.com/aptible/supercronic/releases
ENV SUPERCRONIC_URL=https://github.com/aptible/supercronic/releases/download/v0.2.29/supercronic-linux-amd64 \
SUPERCRONIC=supercronic-linux-amd64 \
SUPERCRONIC_SHA1SUM=cd48d45c4b10f3f0bfdd3a57d054cd05ac96812b
RUN curl -fsSLO "$SUPERCRONIC_URL" \
&& echo "${SUPERCRONIC_SHA1SUM} ${SUPERCRONIC}" | sha1sum -c - \
&& chmod +x "$SUPERCRONIC" \
&& mv "$SUPERCRONIC" "/usr/local/bin/${SUPERCRONIC}" \
&& ln -s "/usr/local/bin/${SUPERCRONIC}" /usr/local/bin/supercronic
CMD ["npm", "run", "start"]
I am still not sure about the fly.toml file part, though?
Maybe it would like this:
# fly.toml app configuration file generated for sb-user-admin-app-v1 on 2024-03-22T11:44:39Z
#
# See https://fly.io/docs/reference/configuration/ for information about how to use this file.
#
app = 'sb-user-admin-app-v1'
primary_region = 'ams'
[build]
[processes]
# web = "bin/rails fly:server" # REMOVE????? // I am not using Rails; I am using NodeJs/remix
cron = "supercronic /app/crontab"
# https://fly.io/docs/apps/processes/ It says:
# Once there’s a [processes] section in your config, flyctl assumes this is a complete list of your processes. If you want an app process group alongside others, add it to the config explicitly.
# So maybe, we should add:
app = 'sb-user-admin-app-v1' # But is this the correct value?
[env]
PORT = "8081"
SHOPIFY_APP_URL = "https://sb-user-admin-app-v1.fly.dev"
SHOPIFY_API_KEY = "[SHOPIFY_API_KEY ]"
SCOPES = "read_checkouts,read_content,read_customers,read_files,read_orders,read_products,write_checkouts,write_customers,write_files,write_orders,write_products,write_themes,write_content"
DATABASE_URL = "file:/data/dev.sqlite"
DEFER_TOKEN = "[DEFER_TOKEN]"
TZ="Europe/London"
[experimental]
cmd = "start_with_migrations.sh"
entrypoint = "sh"
[http_service]
internal_port = 8081
force_https = true
auto_stop_machines = true
auto_start_machines = true
min_machines_running = 0
processes = ['app'] # KEEP????? // My remix app has been installed at /app
[mounts]
source = "sb_user_admin_app_v1_data"
destination = "/data"
[[vm]]
memory = '1gb'
cpu_kind = 'shared'
cpus = 1
Hi Charles,
Did you find out something new?
Thank you
Yes. I am using node-cron, which doesn’t require a cron installation.
It is incredibly easy to install and use. Here is a sample method I built that I call from my action() method:
let job = {};
function createCron(action, shop, process){
const cron = require('node-cron');
const cronTime = process.env.ENVIRONMENT === 'prod' ? '30 1 * * * ' : '30 * * * * * ';
let error = false;
const tasks = cron.getTasks();
let deferReadOrdersTaskExists = false;
for (let [key, value] of tasks.entries()) {
if(value.options.name === 'deferReadOrders-task'){
deferReadOrdersTaskExists = true;
break;
}
}
if(!deferReadOrdersTaskExists){
job = cron.schedule(cronTime, async function execute() {
const date = new Date().toLocaleString();
const days = [14,7,3];
const res = deferReadOrders(days, shop, process);
},{
name: 'deferReadOrders-task',
scheduled: false
});
}
try{
action == 'stop' ? job.stop() : job.start();
}
catch(error){
job.stop();
error = true;
}
return json({
cronTime,
action,
error
});
}