Removing a bunch of old stuff

This commit is contained in:
Eric Allam
2023-06-21 12:39:46 +01:00
parent 25f9aa8c2d
commit fd94a32b95
37 changed files with 36 additions and 1809 deletions
-8
View File
@@ -1,8 +0,0 @@
# You need to stop and re-run docker to switch, `pnpm run docker:db`
# To login using GitHub and connect via OAuth with most integrations
AUTH_CALLBACK_URL=http://localhost:3004/oauth/callback
# To connect with Slack
# AUTH_CALLBACK_URL=https://<ngrok subdomain>.eu.ngrok.io/oauth/callback
# You only need to use this locally if you specify PIZZLY_SECRET_KEY in the webapp .env file
# PIZZLY_SECRET_KEY=<secret_key>
+36 -43
View File
@@ -1,74 +1,67 @@
FROM node:16-bullseye AS pruner
RUN apt-get update && apt-get install openssl -y
FROM node:18-bullseye-slim AS pruner
RUN apt-get update && apt-get install -y openssl
WORKDIR /app
RUN npm install turbo@1.7.0 -g
RUN yarn global add turbo
COPY . .
RUN turbo prune --scope=webapp --docker
RUN find . -name "node_modules" -type d -prune -exec rm -rf '{}' +
# Base strategy to have layer caching
FROM node:16-bullseye AS base
RUN apt-get update && apt-get install openssl ca-certificates g++ make wget python3 -y
ENV PULSAR_CPP_CLIENT_VERSION=2.10.3
RUN wget https://archive.apache.org/dist/pulsar/pulsar-${PULSAR_CPP_CLIENT_VERSION}/DEB/apache-pulsar-client.deb -q
RUN wget https://archive.apache.org/dist/pulsar/pulsar-${PULSAR_CPP_CLIENT_VERSION}/DEB/apache-pulsar-client-dev.deb -q
RUN dpkg -i ./apache-pulsar-client*.deb
FROM node:18-bullseye-slim AS base
RUN apt-get update && apt-get install -y openssl
WORKDIR /app
COPY .gitignore .gitignore
COPY --from=pruner /app/out/json/ .
COPY --from=pruner /app/out/pnpm-lock.yaml ./pnpm-lock.yaml
COPY --from=pruner /app/out/pnpm-workspace.yaml ./pnpm-workspace.yaml
FROM base AS dev-deps
WORKDIR /app
RUN corepack enable
RUN pnpm install --ignore-scripts --no-frozen-lockfile
FROM base AS production-deps
WORKDIR /app
RUN npm install turbo@1.7.0 -g
RUN corepack enable
ENV NODE_ENV production
RUN npm config set python /usr/bin/python3
COPY --from=pruner /app/out/full/apps/webapp/prisma/schema.prisma /app/apps/webapp/prisma/schema.prisma
RUN pnpm install --prod --frozen-lockfile
RUN pnpx prisma generate --schema /app/apps/webapp/prisma/schema.prisma
RUN pnpm install --prod --no-frozen-lockfile
COPY --from=pruner /app/out/full/packages/database/prisma/schema.prisma /app/packages/database/prisma/schema.prisma
RUN pnpx prisma generate --schema /app/packages/database/prisma/schema.prisma
FROM base AS builder
WORKDIR /app
RUN npm install turbo@1.7.0 -g
COPY turbo.json turbo.json
RUN corepack enable
# ENV NODE_ENV production
COPY --from=pruner /app/out/full/ .
RUN npm config set python /usr/bin/python3
ENV NODE_ENV development
RUN pnpm install --ignore-scripts --frozen-lockfile
ENV NODE_ENV production
COPY --from=dev-deps /app/ .
COPY turbo.json turbo.json
RUN pnpm run generate
RUN pnpm run build --filter=webapp...
RUN pnpx prisma migrate deploy --schema apps/webapp/prisma/schema.prisma
RUN pnpm run db:seed --filter=webapp
# Runner
FROM node:16-bullseye AS runner
RUN apt-get update && apt-get install openssl ca-certificates g++ make wget python3 -y
ENV PULSAR_CPP_CLIENT_VERSION=2.10.3
RUN wget https://archive.apache.org/dist/pulsar/pulsar-${PULSAR_CPP_CLIENT_VERSION}/DEB/apache-pulsar-client.deb -q
RUN wget https://archive.apache.org/dist/pulsar/pulsar-${PULSAR_CPP_CLIENT_VERSION}/DEB/apache-pulsar-client-dev.deb -q
RUN dpkg -i ./apache-pulsar-client*.deb
RUN npm install turbo -g
FROM node:18-bullseye-slim AS runner
RUN apt-get update && apt-get install -y openssl
WORKDIR /app
RUN corepack enable
ENV NODE_ENV production
RUN addgroup --system --gid 1001 nodejs
RUN adduser --system --uid 1001 remixjs
RUN chown -R remixjs:nodejs /app
USER remixjs
# RUN addgroup --system --gid 1001 nodejs
# RUN adduser --system --uid 1001 remixjs
# RUN chown -R remixjs:nodejs /app
# USER remixjs
# COPY --from=pruner --chown=remixjs:nodejs /app/out/full/ .
# COPY --from=production-deps --chown=remixjs:nodejs /app .
# COPY --from=builder --chown=remixjs:nodejs /app/apps/remix-app/app/styles/tailwind.css ./apps/remix-app/app/styles/tailwind.css
# COPY --from=builder --chown=remixjs:nodejs /app/apps/remix-app/build/server.js ./apps/remix-app/build/server.js
# COPY --from=builder --chown=remixjs:nodejs /app/apps/remix-app/build ./apps/remix-app/build
# COPY --from=builder --chown=remixjs:nodejs /app/apps/remix-app/public ./apps/remix-app/public
COPY --from=pruner /app/out/full/ .
COPY --from=production-deps /app .
COPY --from=builder /app/apps/remix-app/app/styles/tailwind.css ./apps/remix-app/app/styles/tailwind.css
COPY --from=builder /app/apps/remix-app/build/server.js ./apps/remix-app/build/server.js
COPY --from=builder /app/apps/remix-app/build ./apps/remix-app/build
COPY --from=builder /app/apps/remix-app/public ./apps/remix-app/public
COPY --from=pruner --chown=remixjs:nodejs /app/out/full/ .
COPY --from=production-deps --chown=remixjs:nodejs /app .
COPY --from=builder --chown=remixjs:nodejs /app/apps/webapp/app/styles/tailwind.css ./apps/webapp/app/styles/tailwind.css
COPY --from=builder --chown=remixjs:nodejs /app/apps/webapp/build/server.js ./apps/webapp/build/server.js
COPY --from=builder --chown=remixjs:nodejs /app/apps/webapp/build ./apps/webapp/build
COPY --from=builder --chown=remixjs:nodejs /app/apps/webapp/public ./apps/webapp/public
COPY --from=builder --chown=remixjs:nodejs /app/apps/webapp/prisma/schema.prisma ./apps/webapp/build/schema.prisma
COPY --from=builder --chown=remixjs:nodejs /app/apps/webapp/prisma/migrations ./apps/webapp/build/migrations
COPY --from=builder --chown=remixjs:nodejs /app/apps/webapp/node_modules/.prisma/client/libquery_engine-debian-openssl-1.1.x.so.node ./apps/webapp/build/libquery_engine-debian-openssl-1.1.x.so.node
# release_command = "pnpx prisma migrate deploy --schema apps/webapp/prisma/schema.prisma"
ENTRYPOINT ["pnpm", "--filter", "webapp", "run", "start"]
-6
View File
@@ -1,6 +0,0 @@
module.exports = {
parserOptions: {
tsconfigRootDir: __dirname,
project: "./tsconfig.json",
},
};
-16
View File
@@ -1,16 +0,0 @@
import { faker } from "@faker-js/faker";
describe("smoke tests", () => {
it("should allow you to register and login", () => {
const loginForm = {
email: `${faker.internet.userName()}@example.com`,
password: faker.internet.password(),
username: faker.internet.userName("Jeanne", "Doe"),
};
cy.then(() => ({ email: loginForm.email })).as("user");
cy.visitAndCheck("/");
cy.findByText("Gospel Stack");
cy.findByRole("button");
});
});
-3
View File
@@ -1,3 +0,0 @@
{
"foo": "bar"
}
-35
View File
@@ -1,35 +0,0 @@
export {};
declare global {
namespace Cypress {
interface Chainable {
/**
* Extends the standard visit command to wait for the page to load
*
* @returns {typeof visitAndCheck}
* @memberof Chainable
* @example
* cy.visitAndCheck('/')
* @example
* cy.visitAndCheck('/', 500)
*/
visitAndCheck: typeof visitAndCheck;
}
}
}
// We're waiting a second because of this issue happen randomly
// https://github.com/cypress-io/cypress/issues/7306
// Also added custom types to avoid getting detached
// https://github.com/cypress-io/cypress/issues/7306#issuecomment-1152752612
// ===========================================================
function visitAndCheck(url: string, waitTime: number = 1000) {
cy.visit(url);
cy.location("pathname").should("contain", url).wait(waitTime);
}
Cypress.Commands.add("visitAndCheck", visitAndCheck);
/*
eslint
@typescript-eslint/no-namespace: "off",
*/
-15
View File
@@ -1,15 +0,0 @@
import "@testing-library/cypress/add-commands";
import "./commands";
Cypress.on("uncaught:exception", (err) => {
// Cypress and React Hydrating the document don't get along
// for some unknown reason. Hopefully we figure out why eventually
// so we can remove this.
if (
/hydrat/i.test(err.message) ||
/Minified React error #418/.test(err.message) ||
/Minified React error #423/.test(err.message)
) {
return false;
}
});
-31
View File
@@ -1,31 +0,0 @@
{
"exclude": [
"../node_modules/@types/jest",
"../node_modules/@testing-library/jest-dom"
],
"include": [
"e2e/**/*",
"support/**/*",
"../node_modules/cypress",
"../node_modules/@testing-library/cypress"
],
"compilerOptions": {
"baseUrl": ".",
"noEmit": true,
"types": ["node", "cypress", "@testing-library/cypress"],
"esModuleInterop": true,
"jsx": "react-jsx",
"moduleResolution": "node",
"target": "es2019",
"strict": true,
"skipLibCheck": true,
"resolveJsonModule": true,
"typeRoots": ["../types", "../node_modules/@types"],
"paths": {
"~/*": ["./app/*"]
}
},
"ts-node": {
"swc": true
}
}
-7
View File
@@ -1,7 +0,0 @@
# Mocks
Use this to mock any third party HTTP resources that you don't have running locally and want to have mocked for local development as well as tests.
Learn more about how to use this at [mswjs.io](https://mswjs.io/)
For an extensive example, see the [source code for kentcdodds.com](https://github.com/kentcdodds/kentcdodds.com/blob/main/mocks/start.ts)
-9
View File
@@ -1,9 +0,0 @@
const { setupServer } = require("msw/node");
const server = setupServer();
server.listen({ onUnhandledRequest: "bypass" });
console.info("🔶 Mock server running");
process.once("SIGINT", () => server.close());
process.once("SIGTERM", () => server.close());
@@ -1,79 +0,0 @@
Currently this repo only has a single [customEvent](https://docs.trigger.dev/triggers/custom-events) trigger:
```ts
import { Trigger, customEvent } from "@trigger.dev/sdk";
new Trigger({
// Give your Trigger a stable ID
id: "hello-world",
name: "Template: Hello World",
// Trigger on the custom event named "your.event", see https://docs.trigger.dev/triggers/custom-events
on: customEvent({
name: "your.event",
}),
// The run functions gets called once per "your.event" event
async run(event, ctx) {
await ctx.waitFor("waiting...", { seconds: 10 });
await ctx.logger.info("Hello world from inside trigger.dev");
},
}).listen();
```
## 📺 Go Live
Once you are happy with your workflow you can deploy it live to Render.com (or another hosting service). You can then send custom events that trigger your workflow using the [sendEvent](https://docs.trigger.dev/reference/send-event) function from the `@trigger.dev/sdk`, or simply by making requests to our [`events`](https://docs.trigger.dev/api-reference/events/sendEvent) API endpoint.
Here is an example of sending the custom event to trigger the workflow contained in this repo using `fetch`:
```ts
const event = {
name: "your.event",
payload: {
hello: "world",
},
};
const response = await fetch("https://app.trigger.dev/api/v1/events", {
method: "POST",
headers: {
"Content-Type": "application/json",
Authorization: `Bearer ${process.env.TRIGGER_API_KEY}`,
},
body: JSON.stringify({
id: randomUUID(),
event,
}),
});
```
## ✍️ Customize
You can easily adapt this workflow to a different event relevant to your app. For example, we have a workflow that runs when a user is created and it looks like this:
```ts
import { Trigger, customEvent } from "@trigger.dev/sdk";
import * as slack from "@trigger.dev/slack";
import { z } from "zod";
new Trigger({
id: "new-user",
name: "New user",
on: customEvent({
name: "user.created",
schema: z.object({ id: z.string() }),
}),
async run(event, ctx) {
const user = await prisma.user.find({
where: { id: event.id },
});
await slack.postMessage("🚨", {
channelName: "new-users",
text: `New user signed up: ${user.email}`,
});
},
}).listen();
```
Be sure to check out more over on our [docs](https://docs.trigger.dev)
-70
View File
@@ -1,70 +0,0 @@
This repo contains a simple CRON job workflow that runs every weekday at 9:00 AM UTC.
It is a great starting point for creating your own scheduled workflows.
To easily create CRON schedules, we recommend using [crontab.guru](https://crontab.guru/).
```ts
import { Trigger, scheduleEvent } from "@trigger.dev/sdk";
new Trigger({
// Give your Trigger a stable ID
id: "cron-basic",
name: "Trigger event at 9am every weekday",
//Trigger this event at 09:00 on every day-of-week from Monday through Friday. (https://crontab.guru/#0_9_*_*_1-5)
on: scheduleEvent({ cron: "0 9 * * 1-5" }),
run: async (event, ctx) => {
// This can be anything - e.g. update your database, send an email or post a daily Slack update etc
// Create a log at the correct time
await ctx.logger.info("Received the cron scheduled event", {
event,
});
},
}).listen();
```
## 🔧 Install
You can easily create a new project interactively based on this template by running:
```sh
npx create-trigger@latest cron-basic
# or
yarn create trigger cron-basic
# or
pnpm create trigger@latest cron-basic
```
Follow the instructions in the CLI to get up and running locally in <30s.
### 🧪 Test it
After successfully running this template locally, head over to your [Trigger.dev Dashboard](https://app.trigger.dev) and you should see your newly created workflow.
## ✍️ Customize
You can easily adapt this workflow for example, we have a workflow that runs once a year on the 1st of January and posts a Slack message wishing our team a Happy New Year.
```ts
import { Trigger, scheduleEvent } from "@trigger.dev/sdk";
import * as slack from "@trigger.dev/slack";
new Trigger({
// Give your Trigger a stable ID
id: "cron-happy-new-year",
name: "Happy New Year!",
//Trigger this event at 12am every 1st of January, every year.
on: scheduleEvent({ cron: "0 12 1 1 *" }),
run: async (event, ctx) => {
// This can be anything - e.g. update your database, send an email or post a daily Slack update etc
// log the event at the correct time
await slack.postMessage("🚨", {
channelName: "happy-new-year",
text: `🎉 Happy New Year team! 🎉 `,
});
},
}).listen();
```
Be sure to check out more over on our [docs](https://docs.trigger.dev)
@@ -1,28 +0,0 @@
## 💻 Run locally
First, in your terminal of choice, clone the repo and install dependencies:
```sh
git clone https://github.com/triggerdotdev/github-issues-to-notion.git
cd github-issues-to-notion
npm install
```
Then create a `.env` file at the root of the repository (it's already gitignored) with your development Trigger.dev API Key and NOTION_DATABASE_ID:
```
TRIGGER_API_KEY=<your api key>
NOTION_DATABASE_ID=<your notion database id> # get this by sharing the URL of your database, the ID is after the name but before the question mark
```
And finally you are ready to run the process:
```sh
npm run dev
```
You should see a message like the following:
```
[trigger.dev] ✨ Connected and listening for events [github-issues-to-notion]
```
@@ -1,193 +0,0 @@
This template contains a [GitHub IssueEvent](https://docs.trigger.dev/integrations/apis/github/events/issues) Trigger that will run whenever an issue action is performed in a GitHub repository. It will then create a new row in a Notion database with details from the GitHub issue.
```ts
import { Trigger } from "@trigger.dev/sdk";
import * as github from "@trigger.dev/github";
import * as notion from "@trigger.dev/notion";
//Change "triggerdotdev/github-issues-to-notion" to your own repo, e.g. "yourorg/yourrepo"
const repo =
process.env.GITHUB_REPOSITORY ?? "triggerdotdev/github-issues-to-notion";
//you can find the database ID in the URL of your Notion database, it's the part after the name but before the question mark
// e.g. for https://www.notion.so/triggerdotdev/Notion-test-page-9257302b0758480ebef110889636f107?pvs=4#7953d4fb90724da89d9df4ad68d5e78a
// the database ID would be: 9257302b0758480ebef110889636f107
const notionDatabaseId = process.env.NOTION_DATABASE_ID;
const notionDatabaseId = process.env.NOTION_DATABASE_ID;
new Trigger({
// Give your Trigger a stable ID
id: "github-issues-to-notion",
name: "New GitHub issues are added to your Notion database",
// This will register a webhook with the repo
// and trigger whenever a new issue is created or modified
on: github.events.issueEvent({
repo,
}),
// The run function will get called once per "issue" event
// See https://docs.trigger.dev/integrations/apis/github/events/issues
run: async (event, ctx) => {
if (!notionDatabaseId) {
throw new Error(
"Please set the NOTION_DATABASE_ID environment variable to the ID of your Notion database"
);
}
//we only want to act when a new issue is opened
if (event.action !== "opened") return;
//a row in a Notion database is added using the createPage API and setting the parent to be the database
await notion.createPage("📃", {
parent: {
database_id: notionDatabaseId,
},
properties: {
//this is the title of the new database row
title: {
title: [
{
text: {
content: event.issue.title,
link: {
url: event.issue.html_url,
},
},
},
],
},
},
//this goes in the body of the new Notion page (i.e. when you click into it)
children: [
{
object: "block",
type: "paragraph",
paragraph: {
rich_text: [
{
type: "text",
text: {
content: event.issue.body ?? "No description provided",
},
},
],
},
},
],
});
},
}).listen();
```
## ✍️ Customize
1. Make sure and update the `repo` parameter to point to a GitHub repository you manage by setting the `GITHUB_REPOSITORY` environment variable.
2. Make sure to set the `NOTION_DATABASE_ID` environment variable to the ID of your Notion database. You can find the database ID in the URL of your Notion database, it's the long number before the question mark
- For this URL https://www.notion.so/triggerdotdev/Notion-test-page-9257302b0758480ebef110889636f107?pvs=4#7953d4fb90724da89d9df4ad68d5e78a
- The database ID is `9257302b0758480ebef110889636f107`
3. Customize the `notion.createPage` call to set properties you want on your Notion database. Note that any properties you set must already exist as columns (in the right format) in the database, otherwise you'll get an error back.
## Extending this example
![Notion database for issues](https://imagedelivery.net/3TbraffuDZ4aEf8KWOmI_w/92daa640-6b6e-4ee4-93d8-d36bea295600/public)
This database has 3 extra columns, they must exist in this format:
- Assignees (multi-select)
- Labels (multi-select)
- GitHub (url)
The code below will set the values of these columns based on the GitHub issue.
```ts
import { Trigger } from "@trigger.dev/sdk";
import * as github from "@trigger.dev/github";
import * as notion from "@trigger.dev/notion";
const repo =
process.env.GITHUB_REPOSITORY ?? "triggerdotdev/github-issues-to-notion";
//todo you can find the database ID in the URL of your Notion database, it's the part after the name
//e.g. https://www.notion.so/triggerdotdev/Notion-test-page-9257302b0758480ebef110889636f107?pvs=4#7953d4fb90724da89d9df4ad68d5e78a
const notionDatabaseId = process.env.NOTION_DATABASE_ID;
new Trigger({
// Give your Trigger a stable ID
id: "github-issues-to-notion",
name: "New GitHub issues are added to your Notion database",
// This will register a webhook with the repo
// and trigger whenever a new issue is created or modified
on: github.events.issueEvent({
repo,
}),
// The run function will get called once per "issue" event
// See https://docs.trigger.dev/integrations/apis/github/events/issues
run: async (event, ctx) => {
if (!notionDatabaseId) {
throw new Error(
"Please set the NOTION_DATABASE_ID environment variable to the ID of your Notion database"
);
}
//we only want to act when a new issue is opened
if (event.action !== "opened") return;
//a row in a Notion database is added using the createPage API and setting the parent to be the database
await notion.createPage("📃", {
parent: {
database_id: notionDatabaseId,
},
properties: {
//this is the title of the new database row
title: {
title: [
{
text: {
content: event.issue.title,
link: {
url: event.issue.html_url,
},
},
},
],
},
//this is the link to the issue on GitHub
GitHub: {
url: event.issue.html_url,
},
//the issue assignees as multi-select options
Assignees: {
multi_select: event.issue.assignees.map((assignee) => ({
name: assignee.login,
})),
},
//the issue labels as multi-select options
Labels: {
multi_select:
event.issue.labels?.map((label) => ({
name: label.name,
})) ?? [],
},
},
//this goes in the body of the new Notion page (i.e. when you click into it)
children: [
{
object: "block",
type: "paragraph",
paragraph: {
rich_text: [
{
type: "text",
text: {
content: event.issue.body ?? "No description provided",
},
},
],
},
},
],
});
},
}).listen();
```
@@ -1,28 +0,0 @@
## 💻 Run locally
First, in your terminal of choice, clone the repo and install dependencies:
```sh
git clone https://github.com/triggerdotdev/github-issues-to-slack.git
cd github-issues-to-slack
npm install
```
Then create a `.env` file at the root of the repository (it's already gitignored) with your development Trigger.dev API Key and GITHUB_REPOSITORY:
```
TRIGGER_API_KEY=<your api key>
GITHUB_REPOSITORY=<your github repository> # e.g. triggerdotdev/trigger.dev
```
And finally you are ready to run the process:
```sh
npm run dev
```
You should see a message like the following:
```
[trigger.dev] ✨ Connected and listening for events [github-issues-to-slack]
```
@@ -1,68 +0,0 @@
This template contains a [GitHub IssueEvent](https://docs.trigger.dev/integrations/apis/github/events/issues) Trigger that will run whenever an issue action is performed in a GitHub repository:
```ts
import { Trigger } from "@trigger.dev/sdk";
import * as github from "@trigger.dev/github";
import * as slack from "@trigger.dev/slack";
// Change "triggerdotdev/github-issues-to-slack" to the repo you want to track e.g. "yourorg/yourrepo"
//NB: GitHub org / usernames are case sensitive.
const repo =
process.env.GITHUB_REPOSITORY ?? "triggerdotdev/github-issues-to-slack";
new Trigger({
// Give your Trigger a stable ID
id: "github-issues-to-slack",
name: "Posts to Slack when a GitHub Issue is created or modified",
// This will register a webhook with the repo
// and trigger whenever a new issue is created or modified
on: github.events.issueEvent({
repo,
}),
// The run function will get called once per "issue" event
// See https://docs.trigger.dev/integrations/apis/github/events/issues
run: async (event, ctx) => {
// Posts a new message to the "github-issues" slack channel.
// See https://docs.trigger.dev/integrations/apis/slack/actions/post-message
// If the channel is private, you'll need to add the Trigger.dev bot to the channel first.
const response = await slack.postMessage("send-to-slack", {
channelName: "github-issues",
// If you include blocks, this text will be used in any notifications.
text: `GitHub issue, *${event.issue.title}* has been *${event.action}*. `,
// Blocks allow you to create richly formatted messages.
// See https://api.slack.com/tools/block-kit-builder
blocks: [
{
type: "section",
text: {
type: "mrkdwn",
text: `GitHub issue, *${event.issue.title}* has been *${event.action}*.`,
},
accessory: {
type: "button",
text: {
type: "plain_text",
text: "View Issue",
emoji: true,
},
value: "View Issue",
url: event.issue.html_url,
action_id: "button-action",
},
},
],
});
},
}).listen();
```
## An example of the message posted to Slack:
![GitHub Issue to Slack](https://imagedelivery.net/3TbraffuDZ4aEf8KWOmI_w/c6a66532-8ab6-4e14-83b6-4333731fe200/public)
## ✍️ Customize
1. Make sure and update the `repo` parameter to point to a GitHub repository you manage by setting the `GITHUB_REPOSITORY` environment variable.
2. Feel free to customize [postMessage](https://docs.trigger.dev/integrations/apis/slack/actions/post-message) call with more data from the [GitHub IssueEvent](https://docs.trigger.dev/integrations/apis/github/events/issues) and change the channel name.
You can also do this with [comments](https://docs.trigger.dev/integrations/apis/github/events/issue-comments) , [pull requests](https://docs.trigger.dev/integrations/apis/github/events/pull-requests), and more.
@@ -1,32 +0,0 @@
## 💻 Run locally
First, in your terminal of choice, clone the repo and install dependencies:
```sh
git clone https://github.com/triggerdotdev/github-stars-to-slack.git
cd github-stars-to-slack
npm install
```
Then create a `.env` file at the root of the repository (it's already gitignored) with your development Trigger.dev API Key and GITHUB_REPOSITORY:
```
TRIGGER_API_KEY=<your api key>
GITHUB_REPOSITORY=<your github repository> # e.g. triggerdotdev/trigger.dev
```
And finally you are ready to run the process:
```sh
npm run dev
```
You should see a message like the following:
```
[trigger.dev] ✨ Connected and listening for events [github-stars-to-slack]
```
## 🧪 Test it
The [README](https://github.com/triggerdotdev/github-stars-to-slack) has more details on how to test this template.
@@ -1,37 +0,0 @@
This template contains a [GitHub newStarEvent](https://docs.trigger.dev/integrations/apis/github/events/new-star) Trigger that will run whenever the specified repository gets a new ⭐️:
```ts
import { Trigger } from "@trigger.dev/sdk";
import * as github from "@trigger.dev/github";
import * as slack from "@trigger.dev/slack";
// Change "triggerdotdev/github-stars-to-slack" to the repo you want to track e.g. "yourorg/yourrepo"
const repo =
process.env.GITHUB_REPOSITORY ?? "triggerdotdev/github-stars-to-slack";
new Trigger({
// Give your Trigger a stable ID
id: "github-stars-to-slack",
name: "GitHub Stars to Slack",
// This will register a webhook with the repo
// and trigger whenever the repo gets a new star
on: github.events.newStarEvent({
repo,
}),
// The run function will get called once per "new star" event
// See https://docs.trigger.dev/integrations/apis/github/events/new-star
run: async (event) => {
// Posts a new message to the "github-stars" slack channel.
// See https://docs.trigger.dev/integrations/apis/slack/actions/post-message
await slack.postMessage("⭐️", {
channelName: "github-stars",
text: `New GitHub star from \n<${event.sender.html_url}|${event.sender.login}>. You now have ${event.repository.stargazers_count} stars!`,
});
},
}).listen();
```
## ✍️ Customize
1. Make sure and update the `repo` parameter to point to a GitHub repository you manage by setting the `GITHUB_REPOSITORY` environment variable.
2. Feel free to customize [postMessage](https://docs.trigger.dev/integrations/apis/slack/actions/post-message) call with more data from the [newStar Event](https://docs.trigger.dev/integrations/apis/github/events/new-star#event) and change the channel name.
-79
View File
@@ -1,79 +0,0 @@
Currently this template only has a single [customEvent](https://docs.trigger.dev/triggers/custom-events) trigger:
```ts
import { Trigger, customEvent } from "@trigger.dev/sdk";
new Trigger({
// Give your Trigger a stable ID
id: "hello-world",
name: "Template: Hello World",
// Trigger on the custom event named "your.event", see https://docs.trigger.dev/triggers/custom-events
on: customEvent({
name: "your.event",
}),
// The run functions gets called once per "your.event" event
async run(event, ctx) {
await ctx.waitFor("waiting...", { seconds: 10 });
await ctx.logger.info("Hello world from inside trigger.dev");
},
}).listen();
```
## 📺 Go Live
Once you are happy with your workflow you can deploy it live to Render.com (or another hosting service). You can then send custom events that trigger your workflow using the [sendEvent](https://docs.trigger.dev/reference/send-event) function from the `@trigger.dev/sdk`, or simply by making requests to our [`events`](https://docs.trigger.dev/api-reference/events/sendEvent) API endpoint.
Here is an example of sending the custom event to trigger the workflow contained in this repo using `fetch`:
```ts
const event = {
name: "your.event",
payload: {
hello: "world",
},
};
const response = await fetch("https://app.trigger.dev/api/v1/events", {
method: "POST",
headers: {
"Content-Type": "application/json",
Authorization: `Bearer ${process.env.TRIGGER_API_KEY}`,
},
body: JSON.stringify({
id: randomUUID(),
event,
}),
});
```
## ✍️ Customize
You can easily adapt this workflow to a different event relevant to your app. For example, we have a workflow that runs when a user is created and it looks like this:
```ts
import { Trigger, customEvent } from "@trigger.dev/sdk";
import * as slack from "@trigger.dev/slack";
import { z } from "zod";
new Trigger({
id: "new-user",
name: "New user",
on: customEvent({
name: "user.created",
schema: z.object({ id: z.string() }),
}),
async run(event, ctx) {
const user = await prisma.user.find({
where: { id: event.id },
});
await slack.postMessage("🚨", {
channelName: "new-users",
text: `New user signed up: ${user.email}`,
});
},
}).listen();
```
Be sure to check out more over on our [docs](https://docs.trigger.dev)
@@ -1,31 +0,0 @@
## 💻 Run locally
First, in your terminal of choice, clone the repo and install dependencies:
```sh
git clone https://github.com/triggerdotdev/resend-welcome-drip-campaign.git
cd resend-welcome-drip-campaign
npm install
```
Then execute the following command to create a `.env` file with your development Trigger.dev API Key:
```sh
echo "TRIGGER_API_KEY=<APIKEY>" >> .env
```
And finally you are ready to run the process:
```sh
npm run dev
```
You should see a message output in your terminal like the following:
```
[trigger.dev] ✨ Connected and listening for events [resend-welcome-drip-campaign]
```
## 🧪 Test it
Visit the [README](https://github.com/triggerdotdev/resend-welcome-drip-campaign) has more details on how to test this template.
@@ -1,110 +0,0 @@
## ✨ Trigger.dev Welcome Drip Campaign with Resend.com
This repo contains a [customEvent](https://docs.trigger.dev/triggers/custom-events) Trigger that will send an example drip email campaign using [Resend.com](https://resend.com/) and [react.email](https://react.email/)
> Sign up to Resend using our [special queue jump link](https://resend.com/secret?ref=trigger) ✨
```ts
new Trigger({
// Give your Trigger a stable ID
id: "resend-welcome-drip-campaign",
name: "Resend.com: Welcome Drip Campaign",
// Trigger on a custom event, see https://docs.trigger.dev/triggers/custom-events
on: customEvent({
name: "new.user",
// Use zod to verify event payload. See https://docs.trigger.dev/guides/zod
schema: z.object({ id: z.string(), email: z.string(), name: z.string() }),
}),
// The run functions gets called once per "new.user" event
async run(event, ctx) {
// Send the initial welcome email. See https://docs.trigger.dev/integrations/apis/resend/actions/send-email
await resend.sendEmail("📧 welcome", {
from: FROM_EMAIL,
replyTo: REPLY_TO_EMAIL,
to: event.email,
subject: "Welcome to Acme!",
react: <WelcomeEmail name={event.name} />,
});
// Wait for 1 hour. See https://docs.trigger.dev/functions/delays
await ctx.waitFor("⏲", { hours: 1 });
// Send a tips email
await resend.sendEmail("📧 tips", {
from: FROM_EMAIL,
replyTo: REPLY_TO_EMAIL,
to: event.email,
subject: "3 tips to get the most out of Acme",
react: <TipsEmail name={event.name} />,
});
return event;
},
}).listen();
```
## ✍️ Customize
We've included two example emails that you should customize to your needs. You can use the react.email preview server locally to preview the emails and live edit them.
You can easily run the email preview server and visit [http://localhost:3000](http://localhost:3000):
```sh
npm run emails
```
You can now edit the emails:
- [welcomeEmail.tsx](src/emails/welcomeEmail.tsx)
- [tipsEmail.tsx](src/emails/tipsEmail.tsx)
### From, Reply To, and Subject lines
You can customize the `from` and `replyTo` options by setting the `FROM_EMAIL` and `REPLY_TO_EMAIL` environment variables:
```
FROM_EMAIL="Trigger.dev <eric@email.trigger.dev>"
REPLY_TO_EMAIL="Eric <eric@trigger.dev>"
```
To customize the subject lines, edit the [index.tsx](src/index.tsx) file.
### Customize the drippiness
You can customize the delays between emails by editing the `ctx.waitFor` call:
```ts
await ctx.waitFor("⏲", { hours: 1 });
```
You can also make your drip campaigns smarter by connecting to your own database and conditionally sending different emails depending on what the user does. To see an example of that check out our [resend example](https://github.com/triggerdotdev/trigger.dev-examples/blob/main/src/examples/resend.tsx).
## 📺 Go Live
Once you are happy with your campaign you can deploy it live to Render.com (or another hosting service). You can then send custom events that trigger your workflow using the [sendEvent](https://docs.trigger.dev/reference/send-event) function from the `@trigger.dev/sdk`, or simply by making requests to our [`events`](https://docs.trigger.dev/api-reference/events/sendEvent) API endpoint.
Here is an example of sending the custom event to trigger the workflow contained in this repo using `fetch`:
```ts
const eventId = ulid();
const event = {
name: "new.user",
payload: {
id: "user_1234",
email: "eric@trigger.dev",
name: "Eric",
},
};
const response = await fetch("https://app.trigger.dev/api/v1/events", {
method: "POST",
headers: {
"Content-Type": "application/json",
Authorization: `Bearer ${process.env.TRIGGER_API_KEY}`,
},
body: JSON.stringify({
id: eventId,
event,
}),
});
```
@@ -1,31 +0,0 @@
## 💻 Run locally
First, in your terminal of choice, clone the repo and install dependencies:
```sh
git clone https://github.com/triggerdotdev/scheduled-healthcheck.git
cd scheduled-healthcheck
npm install
```
Then execute the following command to create a `.env` file with your development Trigger.dev API Key:
```sh
echo "TRIGGER_API_KEY=<APIKEY>" >> .env
```
And finally you are ready to run the process:
```sh
npm run dev
```
You should see a message output in your terminal like the following:
```
[trigger.dev] ✨ Connected and listening for events [scheduled-healthcheck]
```
## 🧪 Test it
Visit the [README](https://github.com/triggerdotdev/scheduled-healthcheck) has more details on how to test this template.
@@ -1,40 +0,0 @@
This template contains a [Scheduled](https://docs.trigger.dev/triggers/scheduled) Trigger that will run every 5 minutes and send a Slack message if a website url returns a non-200 response:
```ts
new Trigger({
// Give your Trigger a stable ID
id: "scheduled-healthcheck",
name: "Scheduled Healthcheck",
// Trigger every 5 minutes, see https://docs.trigger.dev/triggers/scheduled
on: scheduleEvent({
rateOf: { minutes: 5 },
}),
// The run functions gets called every 5 minutes
async run(event, ctx) {
// Fetch the website using generic fetch, see https://docs.trigger.dev/functions/fetch
const response = await ctx.fetch("🧑‍⚕️", WEBSITE_URL, {
method: "GET",
retry: {
enabled: false, // Disable retrying
},
});
// If the website is down (or we are in a test run), send a message to Slack
if (!response.ok || ctx.isTest) {
// Post a message to Slack, see https://docs.trigger.dev/integrations/apis/slack/actions/post-message
await slack.postMessage("🤒", {
channelName: "health-checks",
text: `😭 ${WEBSITE_URL} is down!`,
});
}
},
}).listen();
```
## ✍️ Customize
- You can set the website url by defining the `WEBSITE_URL` environment variable.
- Customize the Slack message and channel name.
- Update the frequency (you can go as frequent as once per minute)
Be sure to check out more over on our [docs](https://docs.trigger.dev)
@@ -1,166 +0,0 @@
This repo contains a [customEvent](https://docs.trigger.dev/triggers/custom-events) Trigger that will send an example drip email campaign using [SendGrid](https://sendgrid.com/).
```ts
import { customEvent, Trigger } from "@trigger.dev/sdk";
import * as sendgrid from "@trigger.dev/sendgrid";
import { z } from "zod";
new Trigger({
id: "sendgrid",
name: "SendGrid",
// Trigger on a custom event, see https://docs.trigger.dev/triggers/custom-events
on: customEvent({
name: "new.user",
// Use zod to verify event payload. See https://docs.trigger.dev/guides/zod
schema: z.object({ id: z.string(), email: z.string(), name: z.string() }),
}),
// The run functions gets called once per "new.user" event
run: async (event, ctx) => {
// Send the initial welcome email. See https://docs.trigger.dev/integrations/apis/sendgrid/actions/mail-send
await sendgrid.mailSend("send-welcome-email", {
from: {
// Your 'from' email needs to be verified in SendGrid. https://docs.sendgrid.com/for-developers/sending-email/sender-identity
email: "john@acme.test",
name: "John from the Acme Corporation",
},
personalizations: [
{
to: [
{
name: event.name,
email: event.email,
},
],
},
],
subject: "Welcome to the Acme Corporation!",
content: [
{
// This can either be text/plain or text/html, text/html in this case
type: "text/html",
value: `<p>Hi ${event.name},</p>
<p>Thanks for signing up to the Acme Corporation. </p>
<p>To get started, we recommend browsing our <a href="https://app.acme.test/templates">templates</a>.</p>
<p>Best,</p>
<p>John</p>
<p>CEO, the Acme Corporation</p>`,
},
],
});
// Wait for 1 hour. See https://docs.trigger.dev/functions/delays
await ctx.waitFor("⏲", { hours: 1 });
// Send the follow up email
await sendgrid.mailSend("send-follow-up-email", {
// Your 'from' email needs to be verified in SendGrid. https://docs.sendgrid.com/for-developers/sending-email/sender-identity
from: {
email: "john@acme.test",
name: "John Doe",
},
personalizations: [
{
to: [
{
name: event.name,
email: event.email,
},
],
},
],
subject: "How are you finding the Acme Corporation?",
content: [
{
// This can either be text/plain or text/html, text/plain in this case
type: "text/plain",
value: `Hi ${event.name},
We hope you're enjoying using our product. If you have any questions, please get in touch!
Best,
John,
CEO, the Acme Corporation`,
},
],
});
},
}).listen();
```
## 🔧 Install
You can easily create a new project interactively based on this template by running:
```sh
npx create-trigger@latest sendgrid-welcome-drip-campaign
# or
yarn create trigger sendgrid-welcome-drip-campaign
# or
pnpm create trigger@latest sendgrid-welcome-drip-campaign
```
Follow the instructions in the CLI to get up and running locally in <30s.
## ✍️ Customize
### Customize the drippiness
You can customize the delays between emails by editing the `ctx.waitFor` call:
```ts
await ctx.waitFor("⏲", { hours: 1 });
```
## 🧪 Test it
After successfully running this template locally, head over to your [Trigger.dev Dashboard](https://app.trigger.dev) and you should see your newly created workflow:
![workflow overview](https://imagedelivery.net/3TbraffuDZ4aEf8KWOmI_w/d87d58e5-b5d6-4032-2ece-4c4d20c23100/public)
Click on the "Test your workflow" button and fill in the JSON needed for [this workflow's](src/index.tsx#L14) customEvent Trigger:
![workflow test](https://imagedelivery.net/3TbraffuDZ4aEf8KWOmI_w/4c6f0510-80dd-49dd-93d4-1087e13f8700/public)
After click "Run Test" you'll be redirected to the Run Details page and you should see a prompt for entering your SendGrid API Key:
![api key 1](https://imagedelivery.net/3TbraffuDZ4aEf8KWOmI_w/0708d833-65c2-415e-4eab-13d9dcb70900/public)
![api key 2](https://imagedelivery.net/3TbraffuDZ4aEf8KWOmI_w/428b0e00-6de4-4e5d-567b-6ae0cb037500/public)
After hitting "Save" the Run will pickup where it left off and make the request to SendGrid to send your email:
![preview](https://imagedelivery.net/3TbraffuDZ4aEf8KWOmI_w/ccdc3467-43ee-408f-7fb2-40a42f344a00/public)
## 📺 Go Live
Once you are happy with your campaign you can deploy it live to Render.com (or another hosting service). You can then send custom events that trigger your workflow [sendEvent](https://docs.trigger.dev/reference/send-event) function from the `@trigger.dev/sdk`, or simply by making requests to our [`events`](https://docs.trigger.dev/api-reference/events/sendEvent) API endpoint.
Here is an example of sending the custom event to trigger the workflow contained in this repo using `fetch`:
```ts
const eventId = ulid();
const event = {
name: "new.user",
payload: {
id: "user_1234",
email: "eric@trigger.dev",
name: "Eric",
},
};
const response = await fetch("https://app.trigger.dev/api/v1/events", {
method: "POST",
headers: {
"Content-Type": "application/json",
Authorization: `Bearer ${process.env.TRIGGER_API_KEY}`,
},
body: JSON.stringify({
id: eventId,
event,
}),
});
```
@@ -1,54 +0,0 @@
This template uses [Supabase Webhooks](https://supabase.com/docs/guides/database/webhooks) with the generic [webhookEvent](https://docs.trigger.dev/reference/webhook-event) trigger to send updates whenever a record is created in a Supabase table to Discord, using [Discord incoming webhooks](https://support.discord.com/hc/en-us/articles/228383668-Intro-to-Webhooks) and our generic [fetch](https://docs.trigger.dev/functions/fetch) function.
```ts
import { Trigger, webhookEvent } from "@trigger.dev/sdk";
const SUPABASE_TABLE = process.env.SUPABASE_TABLE ?? "users";
const DISCORD_WEBHOOK_URL = process.env.DISCORD_WEBHOOK_URL;
new Trigger({
// Give your Trigger a stable ID
id: "supabase-to-discord",
name: "Supabase to Discord",
// Trigger on a webhook event, see https://docs.trigger.dev/triggers/webhooks
on: webhookEvent({
service: "supabase", // this is arbitrary, you can set it to whatever you want
eventName: "row.inserted", // this is arbitrary, you can set it to whatever you want
filter: {
type: ["INSERT"], // only trigger on INSERT events
table: [SUPABASE_TABLE], // only trigger
},
}),
// The payload of the webhook is passed as the event argument
async run(event, ctx) {
// Check that the DISCORD_WEBHOOK_URL environment variable is set
if (!DISCORD_WEBHOOK_URL) {
throw new Error("DISCORD_WEBHOOK_URL is not set");
}
// Craft a message to send to Discord
const message = {
embeds: [
{
color: 0x7289da,
title: `New row created in ${event.table}: ${event.record.email}`,
},
],
};
// Send the message to Discord using the incoming webhook URL
await ctx.fetch("✨", DISCORD_WEBHOOK_URL, {
method: "POST",
headers: {
"Content-Type": "application/json",
},
body: message,
});
},
}).listen();
```
## ✍️ Customize
1. Change the table using the `SUPABASE_TABLE` environment variable to point to the table you'd like events from in your supabase database.
2. Feel free to customize the message to Discord by referencing [their docs](https://discord.com/developers/docs/resources/webhook#execute-webhook)
@@ -1,55 +0,0 @@
This template uses [Supabase Webhooks](https://supabase.com/docs/guides/database/webhooks) with the generic [webhookEvent](https://docs.trigger.dev/reference/webhook-event) trigger to send updates whenever a user record is created in a Supabase table to [Loops.so](https://loops.so), the Loops.so API and our generic [fetch](https://docs.trigger.dev/functions/fetch) function.
```ts
import { secureString, Trigger, webhookEvent } from "@trigger.dev/sdk";
new Trigger({
// Give your Trigger a stable ID
id: "supabase-to-loops",
name: "Supabase to Loops.so",
// Trigger on a webhook event, see https://docs.trigger.dev/triggers/webhooks
on: webhookEvent({
service: "supabase", // this is arbitrary, you can set it to whatever you want
eventName: "user.inserted", // this is arbitrary, you can set it to whatever you want
filter: {
type: ["INSERT"], // only trigger on INSERT events
table: ["users"], // only trigger on the users table
},
}),
// The payload of the webhook is passed as the event argument
async run(event, ctx) {
if (!process.env.LOOPS_API_KEY) {
throw new Error("Missing LOOPS_API_KEY environment variable");
}
await ctx.fetch(
"Send to Loops",
"https://app.loops.so/api/v1/contacts/create",
{
method: "POST",
headers: {
Accept: "application/json",
Authorization: secureString`Bearer ${process.env.LOOPS_API_KEY}`,
},
body: {
email: event.record.email,
createdAt: event.record.created_at,
firstName: event.record.first_name,
lastName: event.record.last_name,
userId: String(event.record.id),
},
}
);
},
}).listen();
```
## 🔁 Get your Loops.so API Key
Follow the instructions in [the Loops.so API docs](https://tryloops.notion.site/API-5b453a52dd7c4b419aa4647410de9770) for how to get your API Key.
Once you have the API Key from Loops, set the `LOOPS_API_KEY` env variable in the `.env` file at the root of this project:
```
LOOPS_API_KEY="your Loops api key here"
```
Binary file not shown.

Before

Width:  |  Height:  |  Size: 332 KiB

-23
View File
@@ -1,23 +0,0 @@
#!/usr/bin/env bash
#
# Licensed to the Apache Software Foundation (ASF) under one
# or more contributor license agreements. See the NOTICE file
# distributed with this work for additional information
# regarding copyright ownership. The ASF licenses this file
# to you under the Apache License, Version 2.0 (the
# "License"); you may not use this file except in compliance
# with the License. You may obtain a copy of the License at
#
# http://www.apache.org/licenses/LICENSE-2.0
#
# Unless required by applicable law or agreed to in writing,
# software distributed under the License is distributed on an
# "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
# KIND, either express or implied. See the License for the
# specific language governing permissions and limitations
# under the License.
#
set -e -x
docker compose exec -it pulsar /pulsar/bin/pulsar-admin topics list public/default
-19
View File
@@ -1,19 +0,0 @@
version: "3.7"
volumes:
pulsardatav:
driver: local
services:
pulsar:
image: apachepulsar/pulsar:2.10.2
ports:
- "6650:6650"
- "8080:8080"
volumes:
- "pulsardatav:/pulsar/data"
command: bin/pulsar standalone
container_name: pulsar
tty: true
stdin_open: true
restart: always
-23
View File
@@ -1,23 +0,0 @@
#!/usr/bin/env bash
#
# Licensed to the Apache Software Foundation (ASF) under one
# or more contributor license agreements. See the NOTICE file
# distributed with this work for additional information
# regarding copyright ownership. The ASF licenses this file
# to you under the Apache License, Version 2.0 (the
# "License"); you may not use this file except in compliance
# with the License. You may obtain a copy of the License at
#
# http://www.apache.org/licenses/LICENSE-2.0
#
# Unless required by applicable law or agreed to in writing,
# software distributed under the License is distributed on an
# "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
# KIND, either express or implied. See the License for the
# specific language governing permissions and limitations
# under the License.
#
set -e -x
until curl http://localhost:8080/admin/v2/brokers/internal-configuration > /dev/null 2>&1 ; do sleep 1; done
-89
View File
@@ -1,89 +0,0 @@
const { exec } = require("child_process");
const fs = require("fs");
const path = require("path");
const fetch = require("node-fetch");
const templatesDir = process.argv[2];
if (!templatesDir) {
console.error("Please provide a path to the templates directory");
process.exit(1);
}
// patch is a path to a patch file
async function patchTemplate(templateName, patch, message) {
const templateDir = path.join(templatesDir, templateName);
if (fs.statSync(templateDir).isDirectory()) {
console.log(`Patching template '${templateName}'`);
// Make sure we're on the main branch and there are no uncommitted changes
await execAsync(`cd ${templateDir} && git checkout main`);
// Make sure there are no uncommitted changes
const preStatus = await execAsync(`cd ${templateDir} && git status`);
if (!preStatus.includes("nothing to commit")) {
console.error(
`There are uncommitted changes in template '${templateName}'`
);
return;
}
// Make sure we're up to date with the remote
await execAsync(`cd ${templateDir} && git pull origin main`);
// Apply the patch to the template repo
await execAsync(`cd ${templateDir} && git apply ${patch}`);
// Check if there are any changes
const status = await execAsync(`cd ${templateDir} && git status`);
if (!status.includes("modified:")) {
console.log(`No changes for template '${templateName}'`);
return;
}
console.log(`Changes for template '${templateName}':`, status);
// Create a commit
await execAsync(
`cd ${templateDir} && git add -A && git commit -m "[triggerbot] ${message}"`
);
// Push to remote
await execAsync(`cd ${templateDir} && git push origin main`);
console.log(`Applied patch ${patch} to template '${templateName}'`);
} else {
console.log(`Skipping '${templateName}'`);
}
}
async function execAsync(command) {
return new Promise((resolve, reject) => {
exec(command, (error, stdout, stderr) => {
if (error) {
reject(error);
} else {
resolve(stdout);
}
});
});
}
// called like so: node scripts/patchTemplates.js /path/to/templates patchFile.patch "Patch message"
async function main() {
// Make a JSON request to https://app.trigger.dev/api/v1/templates and parse the response as an array of templates
const templates = await fetch(
"https://app.trigger.dev/api/v1/templates"
).then((res) => res.json());
for (const template of templates) {
try {
await patchTemplate(template.slug, process.argv[3], process.argv[4]);
} catch (error) {
console.log(`Failed to update template '${template.slug}'`, error);
}
}
}
main().catch(console.error);
@@ -1,23 +0,0 @@
From a15d8456dfb82b88137d40e0fc0202dcc8134231 Mon Sep 17 00:00:00 2001
From: Eric Allam <eallam@icloud.com>
Date: Thu, 2 Mar 2023 22:46:05 +0000
Subject: [PATCH] Update package.json
---
package.json | 3 +++
1 file changed, 3 insertions(+)
diff --git a/package.json b/package.json
index f1616fe..d87cec6 100644
--- a/package.json
+++ b/package.json
@@ -25,5 +25,8 @@
"tsup": "^6.5.0",
"tsx": "^3.12.2",
"typescript": "^4.9.4"
+ },
+ "triggerdotdev": {
+ "template": "hello-world"
}
}
-146
View File
@@ -1,146 +0,0 @@
const { exec } = require("child_process");
const fs = require("fs");
const path = require("path");
const fetch = require("node-fetch");
const templatesDir = process.argv[2];
if (!templatesDir) {
console.error("Please provide a path to the templates directory");
process.exit(1);
}
async function updateTemplate(templateName, branchName) {
const templateDir = path.join(templatesDir, templateName);
if (fs.statSync(templateDir).isDirectory()) {
console.log(
`Updating dependencies to @next for template '${templateName}'`
);
// Get the current branch and exit unless it's main
const currentBranch = await execAsync(
`cd ${templateDir} && git rev-parse --abbrev-ref HEAD`
);
if (currentBranch.trim() !== "main") {
console.error(
`Current branch is '${currentBranch.trim()}' for template '${templateName}', exiting.`
);
return;
}
// Make sure we're on the main branch and there are no uncommitted changes
await execAsync(`cd ${templateDir} && git checkout main`);
// Make sure there are no uncommitted changes
const preStatus = await execAsync(`cd ${templateDir} && git status`);
if (!preStatus.includes("nothing to commit")) {
console.error(
`There are uncommitted changes in template '${templateName}'`
);
return;
}
// Make sure we're up to date with the remote
await execAsync(`cd ${templateDir} && git pull origin main`);
// Create a new branch
await execAsync(`cd ${templateDir} && git checkout -b ${branchName}`);
// Find all the dependencies that start with @trigger.dev/
const packageJson = JSON.parse(
fs.readFileSync(path.join(templateDir, "package.json"))
);
const dependencies = Object.keys(packageJson.dependencies).filter((dep) =>
dep.startsWith("@trigger.dev/")
);
if (!dependencies) {
console.error(`No dependencies defined for template '${templateName}'`);
return;
}
const npmInstallCommand = `npm install ${dependencies
.map((dep) => `${dep}@next`)
.join(" ")}`;
console.log(`Attempting ${npmInstallCommand}`);
await execAsync(`cd ${templateDir} && ${npmInstallCommand}`);
// Check if there are any changes
const status = await execAsync(`cd ${templateDir} && git status`);
if (!status.includes("modified:")) {
console.log(`No changes for template '${templateName}'`);
return;
}
console.log(`Changes for template '${templateName}':`, status);
// Create a commit
await execAsync(
`cd ${templateDir} && git add package.json package-lock.json && git commit -m "[triggerbot] Updated packages to @next ${dependencies.join(
", "
)}"`
);
// Push to remote
await execAsync(`cd ${templateDir} && git push origin ${branchName}`);
console.log(`Prerelease dependencies for template '${templateName}'`);
} else {
console.log(`Skipping '${templateName}'`);
}
}
async function execAsync(command) {
return new Promise((resolve, reject) => {
exec(command, (error, stdout, stderr) => {
if (error) {
reject(error);
} else {
resolve(stdout);
}
});
});
}
async function main() {
// Get the branch name from the args
const branchName = process.argv[3];
if (!branchName) {
console.error("Please provide a branch name");
process.exit(1);
}
const templateSlug = process.argv[4];
if (templateSlug) {
try {
await updateTemplate(templateSlug, branchName);
} catch (error) {
console.log(`Failed to update template '${templateSlug}'`, error);
}
return;
}
// Make a JSON request to https://app.trigger.dev/api/v1/templates and parse the response as an array of templates
const templates = await fetch(
"https://app.trigger.dev/api/v1/templates"
).then((res) => res.json());
for (const template of templates) {
try {
await updateTemplate(template.slug, branchName);
} catch (error) {
console.log(`Failed to update template '${template}'`, error);
}
}
}
main().catch(console.error);
-23
View File
@@ -1,23 +0,0 @@
#!/usr/bin/env bash
#
# Licensed to the Apache Software Foundation (ASF) under one
# or more contributor license agreements. See the NOTICE file
# distributed with this work for additional information
# regarding copyright ownership. The ASF licenses this file
# to you under the Apache License, Version 2.0 (the
# "License"); you may not use this file except in compliance
# with the License. You may obtain a copy of the License at
#
# http://www.apache.org/licenses/LICENSE-2.0
#
# Unless required by applicable law or agreed to in writing,
# software distributed under the License is distributed on an
# "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
# KIND, either express or implied. See the License for the
# specific language governing permissions and limitations
# under the License.
#
set -e -x
ngrok http --subdomain=${1:-$NGROK_SUBDOMAIN} --region ${2:-eu} 3004
-23
View File
@@ -1,23 +0,0 @@
#!/usr/bin/env bash
#
# Licensed to the Apache Software Foundation (ASF) under one
# or more contributor license agreements. See the NOTICE file
# distributed with this work for additional information
# regarding copyright ownership. The ASF licenses this file
# to you under the Apache License, Version 2.0 (the
# "License"); you may not use this file except in compliance
# with the License. You may obtain a copy of the License at
#
# http://www.apache.org/licenses/LICENSE-2.0
#
# Unless required by applicable law or agreed to in writing,
# software distributed under the License is distributed on an
# "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
# KIND, either express or implied. See the License for the
# specific language governing permissions and limitations
# under the License.
#
set -e -x
ngrok http --subdomain=${1:-$NGROK_SUBDOMAIN} --region ${2:-eu} 3000
-23
View File
@@ -1,23 +0,0 @@
#!/usr/bin/env bash
#
# Licensed to the Apache Software Foundation (ASF) under one
# or more contributor license agreements. See the NOTICE file
# distributed with this work for additional information
# regarding copyright ownership. The ASF licenses this file
# to you under the Apache License, Version 2.0 (the
# "License"); you may not use this file except in compliance
# with the License. You may obtain a copy of the License at
#
# http://www.apache.org/licenses/LICENSE-2.0
#
# Unless required by applicable law or agreed to in writing,
# software distributed under the License is distributed on an
# "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
# KIND, either express or implied. See the License for the
# specific language governing permissions and limitations
# under the License.
#
set -e -x
ngrok http --subdomain=${1:-$NGROK_SUBDOMAIN} --region ${2:-eu} 8889
-143
View File
@@ -1,143 +0,0 @@
const { exec } = require("child_process");
const fs = require("fs");
const path = require("path");
const fetch = require("node-fetch");
const readline = require("node:readline");
const templatesDir = process.argv[2];
if (!templatesDir) {
console.error("Please provide a path to the templates directory");
process.exit(1);
}
async function updateTemplate(templateName) {
const templateDir = path.join(templatesDir, templateName);
if (fs.statSync(templateDir).isDirectory()) {
const currentBranch = (
await execAsync(`cd ${templateDir} && git rev-parse --abbrev-ref HEAD`)
).trim();
console.log(
`Updating dependencies for template '${templateName}' in current branch '${currentBranch}'`
);
// Ask the user if they want to update the template (default to yes)
const updateTemplate = await new Promise((resolve) => {
const rl = readline.createInterface({
input: process.stdin,
output: process.stdout,
});
rl.question(
`Update dependencies for template '${templateName}' in branch ${currentBranch}? [Y/n] `,
(answer) => {
rl.close();
resolve(answer.toLowerCase() !== "n");
}
);
});
if (!updateTemplate) {
console.log(`Skipping '${templateName}'`);
return;
}
// Make sure we're on the main branch and there are no uncommitted changes
await execAsync(`cd ${templateDir} && git checkout ${currentBranch}`);
// Make sure there are no uncommitted changes
const preStatus = await execAsync(`cd ${templateDir} && git status`);
if (!preStatus.includes("nothing to commit")) {
console.error(
`There are uncommitted changes in template '${templateName}'`
);
return;
}
// Make sure we're up to date with the remote
await execAsync(`cd ${templateDir} && git pull origin ${currentBranch}`);
// Find all the dependencies that start with @trigger.dev/
const packageJson = JSON.parse(
fs.readFileSync(path.join(templateDir, "package.json"))
);
const dependencies = Object.keys(packageJson.dependencies).filter((dep) =>
dep.startsWith("@trigger.dev/")
);
if (!dependencies) {
console.error(`No dependencies defined for template '${templateName}'`);
return;
}
const npmInstallCommand = `npm install ${dependencies
.map((dep) => `${dep}@latest`)
.join(" ")}`;
console.log(`Attempting ${npmInstallCommand}`);
await execAsync(
`cd ${templateDir} && npm install ${dependencies
.map((dep) => `${dep}@latest`)
.join(" ")}`
);
// Check if there are any changes
const status = await execAsync(`cd ${templateDir} && git status`);
if (!status.includes("modified:")) {
console.log(`No changes for template '${templateName}'`);
return;
}
console.log(`Changes for template '${templateName}':`, status);
// Create a commit
await execAsync(
`cd ${templateDir} && git add package.json package-lock.json && git commit -m "[triggerbot] Updated packages ${dependencies.join(
", "
)}"`
);
// Push to remote
await execAsync(`cd ${templateDir} && git push origin ${currentBranch}`);
console.log(`Updated dependencies for template '${templateName}'`);
} else {
console.log(`Skipping '${templateName}'`);
}
}
async function execAsync(command) {
console.log(`Executing command: ${command}`);
return new Promise((resolve, reject) => {
exec(command, (error, stdout, stderr) => {
if (error) {
reject(error);
} else {
resolve(stdout);
}
});
});
}
async function main() {
// Make a JSON request to https://app.trigger.dev/api/v1/templates and parse the response as an array of templates
const templates = await fetch(
"https://app.trigger.dev/api/v1/templates"
).then((res) => res.json());
for (const template of templates) {
try {
await updateTemplate(template.slug);
} catch (error) {
console.log(`Failed to update template '${template}'`, error);
}
}
}
main().catch(console.error);