diff --git a/sites/upsun/src/get-started/stacks/express.md b/sites/upsun/src/get-started/stacks/express.md deleted file mode 100644 index b0e2d9c4e7..0000000000 --- a/sites/upsun/src/get-started/stacks/express.md +++ /dev/null @@ -1,40 +0,0 @@ ---- -title: Deploying Express on Upsun -sidebarTitle: Express -sectionBefore: Javascript/Node.js -weight: -100 -description: | - Welcome to the Upsun documentation specific to the Express framework on Upsun. - It includes common reference materials useful for deploying Express, but also external community and blog resources that cover more advanced topics relevant for the framework. ---- - -{{< note title="Hello, there!" theme="info" >}} - -{{% description %}} - -Before you proceed, be sure to checkout the [{{% vendor/name %}} demo app](https://console.upsun.com/projects/create-project) and the main [Getting started guide](/get-started/here/_index.md). These two resources provide all of the core concepts and common commands you'll need to know before using the materials below. - -{{< /note >}} - -## Getting started - -- [Upsun demo application](https://console.upsun.com/projects/create-project) -- [Upsun Getting started guide](/get-started/here/_index.md) -- [What is Upsun?](/learn/overview) - -## Documentation - -- [JavaScript/Node.js documentation](/languages/nodejs/) -- [Managing dependencies](/languages/nodejs#dependencies) - -## Community content - -- [ExpressJS topics](https://support.platform.sh/hc/en-us/search?utf8=%E2%9C%93&query=express) -- [Node.js topics](https://support.platform.sh/hc/en-us/search?utf8=%E2%9C%93&query=node) -- [JavaScript topics](https://support.platform.sh/hc/en-us/search?utf8=%E2%9C%93&query=js) - -## Blogs - -- [A quick-start guide on hosting Express on Upsun](https://upsun.com/blog/setting-up-express-on-upsun/) - - diff --git a/sites/upsun/src/get-started/stacks/express/_index.md b/sites/upsun/src/get-started/stacks/express/_index.md new file mode 100644 index 0000000000..d0139a78ee --- /dev/null +++ b/sites/upsun/src/get-started/stacks/express/_index.md @@ -0,0 +1,344 @@ +--- +title: Deploying Express on Upsun +sectionBefore: Javascript/Node.js +sidebarTitle: Express +weight: -100 +layout: single +description: | + Complete the last required steps to successfully deploy Express on {{% vendor/name %}}. +--- + +{{< note title="Note" theme="info" >}} + +Before you start, check out the [{{% vendor/name %}} demo app](https://console.upsun.com/projects/create-project) and the main [Getting started guide](/get-started/here/_index.md). +They provide all of the core concepts and common commands you need to know before using the materials below. + +{{< /note >}} + +{{% guides/requirements name="Express" %}} + +## 1. Create an Express app + +To create your Express app, follow these steps. + +1. Follow the Express [installation guide](https://expressjs.com/en/starter/installing.html). + To fast track the process, run the following commands: + + ```bash {location="Terminal"} + mkdir my-express-app && cd my-express-app + npx express-generator + ``` + +2. To initialize the local Git repository and commit local files, run the following commands: + + ```bash {location="Terminal"} + git init + echo "node_modules" >> .gitignore + git add . + git commit -m "Init Express application." + ``` + +{{< note theme="info" >}} +You can view your running app locally by installing dependencies (`npm install`) and running `npm run dev`. +The local server is visible at `localhost:3000`. +{{< /note >}} + +## 2. Create a new project + +To create a project on {{% vendor/name %}}, +follow these steps. + +{{< note title="Remember" >}} +After creating your {{% vendor/name %}} project, copy your new **project ID** for later use. +{{< /note >}} + +{{< codetabs >}} ++++ +title=Using the CLI ++++ +To create a new project with the {{% vendor/name %}} CLI, use the following command and follow the prompts: + +```bash {location="Terminal"} +{{% vendor/cli %}} project:create +``` + +{{< note >}} + +When creating a new project using the {{% vendor/name %}} CLI command `project:create`, +you are asked if you want to set the local remote to your new project. Enter **Yes (y)**. + +Your local source code is automatically linked to your newly created {{% vendor/name %}} project +through the creation of a `.{{% vendor/cli %}}/local/project.yaml`. +This file contains the corresponding `` for the {{% vendor/name %}} CLI to use, +and sets a Git remote to `{{% vendor/cli %}}`. + +{{< /note >}} + +<---> ++++ +title=Using the Console ++++ + +1. Create an organization or select an existing one. + +2. Click **Create from scratch**. + +3. Fill in details like the project name and [region](/development/regions.md). + + {{% note %}} + + You can define resources for your project later on, after your first push. + + {{% /note %}} + +4. To link your local source code to your new {{% vendor/name %}} project, + run the following command: + + ```bash {location="Terminal"} + {{% vendor/cli %}} project:set-remote + ``` + + This command adds a new remote called `{{% vendor/cli %}}` to your local Git repository, + which is equivalent to the following commands: + + ```bash {location="Terminal"} + git remote + origin + {{% vendor/cli %}} + ``` + + It also creates a new `.{{% vendor/cli %}}/local/project.yaml` file that contains the `` + for the `{{% vendor/cli %}}` CLI to use. + + {{< note theme="info" title="Tip" >}} + + If you forget your ``, run the following command and find your project in the list: + + ```bash {location="Terminal"} + {{% vendor/cli %}} project:list + ``` + {{< /note >}} + +{{< /codetabs >}} + +## 3. Choose your Git workflow + +You can use {{% vendor/name %}} projects as a classic Git repository, +where you are able to push your source code in different ways, +using either the Git CLI or the {{% vendor/name %}} CLI. +You can choose which way —or Git workflow— you want to use for your project from the following options: + +- Your project source code is **hosted on a {{% vendor/name %}} Git repository** +- Your project source code is **hosted on your own GitHub repository** + +{{< codetabs >}} ++++ +title={{% vendor/name %}} Git repository ++++ +For the rest of this guide, you will use the normal Git workflow (`git add . && git commit -m "message" && git push {{% vendor/cli %}}`) to commit your source code changes to Git history. +You will also use the {{% vendor/name %}} CLI to deploy your [{{% vendor/name %}} environment](/environments.html) with the latest code updates. + +<---> ++++ +title=GitHub repository ++++ +{{% vendor/name %}} provides a [Github integration](integrations/source/github.md) that allows your {{% vendor/name %}} project to be fully integrated with your Github repository. +This enables you, as a developer, to use a normal Git workflow (`git add . && git commit -m "message" && git push`) to deploy your environment—with no need to connect to the {{% vendor/name %}} Console. + +{{< note >}} +Make sure you complete the following steps before adding a [Github integration](integrations/source/github.md): + +1. Create a Git repository in your own organization following the relevant [Github repository creation guide](https://docs.github.com/en/repositories/creating-and-managing-repositories/creating-a-new-repository). +2. Create a [Github integration](integrations/source/github.md). +3. Add a Git remote to your local project, from the root of your Express directory.
+ To do so, run the following commands: + + ```bash {location="Terminal"} + git remote add origin + git add . && git commit -m "init express" + git push origin + ``` +{{< /note >}} + +{{< /codetabs >}} + +## 4. Configure your project + +To host your Express application on {{% vendor/name %}}, +you need to have a few YAML configuration files at the root of your project. +These files manage your app's behavior. +They are located in a `.{{% vendor/cli %}}/` folder at the root of your source code +and structured in a similar way to this: + +```txt +my-express-app +├── .{{% vendor/cli %}} +│ └── config.yaml +├── [.environment] +└── +``` + +To generate these files, run the following command at the root of your project: + +``` {location="Terminal"} +{{% vendor/cli %}} project:init +``` + +Follow the prompts. + +To commit your new files, run the following commands: + +```bash {location="Terminal"} +git add . +git commit -m "Add {{% vendor/name %}} config files" +``` + +## 5. Deploy + +And just like that, it’s time to deploy! + +Depending on the Git workflow you chose at the beginning of this tutorial, +there are two ways to deploy your source code changes. + +{{< codetabs >}} + ++++ +title=Using {{% vendor/name %}} Git repository ++++ + +You can push your code using the normal Git workflow (`git add . && git commit -m "message" && git push`). This pushes your source code changes to your `{{% vendor/cli %}}` remote repository. Alternatively, you can use the following {{% vendor/name %}} CLI command: + +```bash {location="Terminal"} +{{% vendor/cli %}} push +``` + +<---> ++++ +title=Using a third-party Git repository ++++ + +When you choose to use a third-party Git hosting service, the {{< vendor/name >}} Git +repository becomes a read-only mirror of the third-party repository. All your +changes take place in the third-party repository. + +Add an integration to your existing third-party repository: + +- [BitBucket](/integrations/source/bitbucket.md) +- [GitHub](/integrations/source/github.md) +- [GitLab](/integrations/source/gitlab.md) + +If you are using an integration, on each code updates, +use the normal Git workflow (`git add . && git commit -m "message" && git push`) to push your code to your external repository. +To do so, run the following command: + +```bash {location="Terminal"} +git push origin +``` + +Your GitHub, GitLab, or Bibucket integration process then automatically deploys changes to your environment. +If you're pushing a new Git branch, a new environment is created. + +{{< /codetabs >}} + +{{% vendor/name %}} then reads your configuration files, +and deploys your project using [default container resources](/manage-resources/resource-init.md). +If you don't want to use those default resources, +define your own [resource initialization strategy](/manage-resources/resource-init.md#define-a-resource-initialization-strategy), +or [amend those default container resources](/manage-resources/adjust-resources.md) after your project is deployed. + +Et voilà, your Express application is live! + +{{< note title="Tip" theme="info" >}} + +Each environment has its own domain name. +To open the URL of your new environment, run the following command: + + ```bash {location="Terminal"} + {{% vendor/cli %}} environment:url --primary + ``` +{{< /note >}} + +## 6. Make changes to your project + +Now that your project is deployed, you can start making changes to it. +For example, you might want to fix a bug or add a new feature. + +In your project, the `main` branch always represents the production environment. +Other branches are for developing new features, fixing bugs, or updating the infrastructure. + +To make changes to your project, follow these steps: + +1. Create a new environment (a Git branch) to make changes without impacting production: + + ```bash {location="Terminal"} + {{% vendor/cli %}} branch feat-a + ``` + + This command creates a new local `feat-a` Git branch based on the main Git branch, + and activates a related environment on {{< vendor/name >}}. + The new environment inherits the data (service data and assets) of its parent environment (the production environment here). + +2. Make changes to your project. + For example, edit the `views/index.jade` file and make the following changes: + + ```diff + diff --git a/views/index.jade b/views/index.jade + index 3d63b9a..77aee43 100644 + --- a/views/index.jade + +++ b/views/index.jade + @@ -2,4 +2,4 @@ extends layout + + block content + h1= title + - p Welcome to #{title} + + p Welcome to #{title} on Upsun + `` + +3. Commit your changes: + + ```bash {location="Terminal"} + git add views/index.jade + git commit -m "Update index page view." + ``` + +4. Deploy your changes to the `feat-a` environment: + + ```bash {location="Terminal"} + {{% vendor/cli %}} push + ``` + +5. Iterate by changing the code, committing, and deploying. + When satisfied with your changes, merge them to the main branch, + and remove the feature branch: + + ```bash {location="Terminal"} + {{% vendor/cli %}} merge + Are you sure you want to merge feat-a into its parent, main? [Y/n] y + {{% vendor/cli %}} checkout main + git pull {{% vendor/cli %}} main + {{% vendor/cli %}} environment:delete feat-a + git fetch --prune + ``` + + Note that deploying to production is fast because the image built for the `feat-a` environment is reused. + + For a long running branch, to keep the code up-to-date with the main branch, use `git merge main` or `git rebase main`. + You can also keep the data in sync with the production environment by using `{{% vendor/cli %}} env:sync`. + +## Further resources + +### Documentation + +- [JavaScript/Node.js documentation](/languages/nodejs/) +- [Managing dependencies](/languages/nodejs#dependencies) +- [Add a database to Express](/get-started/stacks/express/add-database) + +### Community content + +- [ExpressJS topics](https://support.platform.sh/hc/en-us/search?utf8=%E2%9C%93&query=express) +- [Node.js topics](https://support.platform.sh/hc/en-us/search?utf8=%E2%9C%93&query=node) +- [JavaScript topics](https://support.platform.sh/hc/en-us/search?utf8=%E2%9C%93&query=js) + +### Blogs + +- [A quick-start guide on hosting Express on Upsun](https://upsun.com/blog/setting-up-express-on-upsun/) diff --git a/sites/upsun/src/get-started/stacks/express/add-database.md b/sites/upsun/src/get-started/stacks/express/add-database.md new file mode 100644 index 0000000000..0291816904 --- /dev/null +++ b/sites/upsun/src/get-started/stacks/express/add-database.md @@ -0,0 +1,234 @@ +--- +title: "Add a database" +weight: -130 +description: | + Once your Express app has been deployed on {{% vendor/name %}}, you might want to add a service to it. +--- + +{{% description %}} + +{{% vendor/name %}} projects already include a [variety of managed services](/add-services.html#available-services), so you don’t have to subscribe to an external cache or search-engine services. + +As these services are included in your project, you can manage them through Git. +They’re backed up along with the rest of your project. +You can add new services and manage existing service configurations from your `.{{% vendor/cli %}}/config.yaml` file. + +For example, to add a [MariaDB database engine](/add-services/mysql.html) to your Express project, complete the following steps: + +## 1. Create a new branch for testing + +To create a new branch, run the following command: + +```bash {location="Terminal"} +{{% vendor/cli %}} environment:branch add-mysql-database +``` + +## 2. Add a MariaDB service + +Configure the MariaDB service by adding a `database` service to your `.{{% vendor/cli %}}/config.yaml` file: + +```yaml {location=".upsun/config.yaml"} +applications: + my-express-app: + source: + root: "/" + type: "nodejs:20" + + [...] + +{{< code-link destination="/add-services.html#available-services" text="services" title="Click to see the complete list of all available services" >}}: + database: + type: mariadb:{{% latest "mariadb" %}} +``` + +To connect the service to your application (``app``), add the following relationship: + +```yaml {location=".upsun/config.yaml"} +applications: + my-express-app: + source: + root: "/" + type: "nodejs:20" + + [...] + + relationships: + database: "database:mysql" + +{{< code-link destination="/add-services.html#available-services" text="services" title="Click to see the complete list of all available services" >}}: + database: + type: mariadb:{{% latest "mariadb" %}} +``` + +Commit your change: + +```bash {location="Terminal"} +git commit -am "adding MariaDb database service" +{{% vendor/cli %}} push +``` + +{{% vendor/name %}} now reads your configuration files and deploys your project using [default container resources](/manage-resources/resource-init.md). +If you don't want to use those default resources, +define your own [resource initialization strategy](/manage-resources/resource-init.md#define-a-resource-initialization-strategy), +or [amend those default container resources](/manage-resources/adjust-resources.md) after your project is deployed. + +## 3. Connect to the service + +To configure your Express app so it uses your new database, +you need a Node.s module named `mysql2`. +To install it, run the following command: + +```bash {location="Terminal"} +npm install mysql2 +``` + +Wherever your application code attemps to connect to the database service, +Upsun will automatically generate environment variables containing connection credentials as a function of the relationship name. + +In this example, the MariaDB service access is granted to the application container via the relationship `database`. +Upsun will therefore generate the variable `DATABASE_HOST` (among many others), using this name. + +Here's an example of how this credential variable naming convention is used to connect to a MariaDB service: + +```javascript {location="index.js"} +const express = require('express') +const app = express() +const mysql = require("mysql2/promise"); +const port = (process.env.PORT || '3000'); + +function openConnection() { + return mysql.createConnection({ + host: process.env.DATABASE_HOST, + port: process.env.DATABASE_PORT, + user: process.env.DATABASE_USERNAME, + password: process.env.DATABASE_PASSWORD, + database: process.env.DATABASE_DATABASE + }); +} + +function createTable(connection) { + return connection.execute( + `CREATE TABLE IF NOT EXISTS {{% vendor/cli %}}info ( + uid INT(10) NOT NULL AUTO_INCREMENT, + username VARCHAR(64) NULL DEFAULT NULL, + departname VARCHAR(128) NULL DEFAULT NULL, + created DATE NULL DEFAULT NULL, + PRIMARY KEY (uid) + ) DEFAULT CHARSET=utf8 COLLATE=utf8_unicode_ci;` + ); +} + +function insertData(connection) { + return connection.execute( + "INSERT INTO {{% vendor/cli %}}info (username, departname, created) VALUES ('{{% vendor/cli %}}', 'Deploy Friday', '2023-09-29')" + ); +} + +function readData(connection) { + return connection.query("SELECT * FROM {{% vendor/cli %}}info"); +} + +function dropTable(connection) { + return connection.execute("DROP TABLE {{% vendor/cli %}}info"); +} + +// Define the main route. +app.get('/', async function(req, res){ + + // Connect to MariaDB. + const connection = await openConnection(); + + await createTable(connection); + await insertData(connection); + + const [rows] = await readData(connection); + + const droppedResult = await dropTable(connection); + + // Make the output. + const outputString = `Hello, World! - A simple Express web framework template for {{% vendor/name %}} + +MariaDB Tests: + +* Connect and add row: + - Row ID (1): ${rows[0].uid} + - Username ({{% vendor/cli %}}): ${rows[0].username} + - Department (Deploy Friday): ${rows[0].departname} + - Created (2023-09-29): ${rows[0].created} +* Delete row: + - Status (0): ${droppedResult[0].warningStatus}`; + + res.set('Content-Type', 'text/plain'); + res.send(outputString); +}); + +// Get PORT and start the server +app.listen(port, function() { + console.log(`Listening on port ${port}`) +}); +``` + +Commit and deploy your changes: + +```bash {location="Terminal"} +git add package.json package-lock.json index.js && git commit -m "adding MariaDb database service" +{{% vendor/cli %}} push +{{% vendor/cli %}} environment:url --primary +``` + +## 4. Merge to production + +When satisfied with your changes, merge them to the main branch: + +```bash {location="Terminal"} +{{% vendor/cli %}} merge +``` + +{{< note >}} +You can [adjust your project resources](/manage-resources/adjust-resources.md) at any time. +{{< /note >}} + +## 5. Remove the feature branch + +Then, remove the feature branch: + +```bash {location="Terminal"} +{{% vendor/cli %}} checkout main +git pull {{% vendor/cli %}} main +{{% vendor/cli %}} environment:delete add-mysql-database +git fetch --prune +``` + +{{< note >}} +When the `environment:delete` CLI command is run, the CLI suggests you deactivate and delete your `add-mysql-database` environment. +Make sure you opt in. +{{< /note >}} + +## Tips & Tricks + +You can get your project's relationship information using the following command: + +```bash {location="Terminal"} +{{% vendor/cli %}} relationships + ... + database: + - + username: user + scheme: mysql + service: mariadb + fragment: null + ip: 198.12.123.45 + hostname: abcdefghijklm1234567890123.mariadb.service._..{{< vendor/urlraw "hostname" >}} + public: false + cluster: abcdefgh1234567-add-mysql-database-abcd123 + host: mariadb.internal + rel: mysql + query: + is_master: true + path: main + password: '' + type: 'mariadb:10.6' + port: 3306 + host_mapped: false + url: 'mysql://user:@mariadb.internal:3306/main' +``` diff --git a/sites/upsun/src/languages/nodejs/_index.md b/sites/upsun/src/languages/nodejs/_index.md index 12a61a6cee..00032730af 100644 --- a/sites/upsun/src/languages/nodejs/_index.md +++ b/sites/upsun/src/languages/nodejs/_index.md @@ -377,6 +377,6 @@ highlight=js All major Javascript/Node.js web frameworks can be deployed on {{% vendor/name %}}. See dedicated guides for deploying and working with them: -- [Express](/get-started/stacks/express.md) +- [Express](/get-started/stacks/express) - [Next.js](/get-started/stacks/nextjs.md) - [Strapi](/get-started/stacks/strapi.md)