01. What is Serverless?

The definition and understanding of Serverless can be interpreted differently in different perspectives and scenarios. AWS defines Serverless(on the AWS Cloud) as “a way to describe the services, practices, and policies that enable you to build more agile applications, To be able to innovate and respond to change more quickly.” Red Hat sees Serverless as a development model that “allows developers to focus on building and running applications without having to manage servers,” and further divides Serverless products into two categories: BaaS(back-end as a service, which gives developers access to a wide variety of third-party services and applications) and FaaS(function as a service, where developers write logic, deploy it into a container managed entirely by the platform, and then execute it on demand). Serverless Framework says Serverless is “a developer – and enterprise-driven movement that allows a single developer to do high-traffic application development while focusing only on delivering value.”

Regardless of the aspect and Angle, Serverless has the following characteristics in common:

  1. Rapid development, rapid deployment
  2. Pay by volume to keep costs down
  3. Automatic expansion without maintenance

At present, they are all implemented based on FaaS services of various cloud vendors, such as SCF of Tencent Cloud, Lambda of AWS, Azure Funcitons of Azure cloud, etc.

What problem does Serverless solve?

As computing power increases, system complexity increases, and user size increases, software problems (below, also known as software crises) grow exponentially.

  • Software development schedules are unpredictable
  • Software development costs are hard to control
  • Software product quality cannot be guaranteed
  • Software products are difficult to maintain

Serverless offers solutions to the software crisis problem in the following ways:

  • System functions can be broken down into smaller granularity by functional means, which makes it easier to design, develop, test and maintain.
  • By charging by volume, the server costs are greatly reduced when resources are idle.
  • Automatic capacity expansion and cloud platform support greatly reduce o&M workload and software maintenance costs.

And in a modern work environment where agile working is now the norm, Serverless also provides development best practices for quickly verifying ideas and iterating capabilities without worrying about code changes affecting the rest of the system, server configuration before deployment, and maintenance after deployment.

02. Serverless Framework

Serverless Framework is a very popular Serverless application Framework in the industry. Through close cooperation with many first-class cloud providers such as Tencent Cloud and AWS, Serverless Framework provides the majority of developers with no need to care about the underlying infrastructure, they can write and deploy code without service development experience.

The Serverless Framework also provides resource management, automatic scaling, and statistical analysis capabilities, so that developers can save operation and maintenance costs. The Serverless Framework allows developers to pay by the amount without having to deal with tasks such as log collection and exception statistics.

Serverless Framework works closely with Tencent Cloud through CLI tools to provide Chinese users with a complete Serverless Components based solution. It covers the entire life cycle of non-service applications such as coding, testing, and deployment, and suits the usage scenarios and habits of Chinese users.

Why Serverless Framework?

With just a few short lines of Serverless Framework configuration files and CLI tools, developers can get additional:

  • Functions can be developed locally and deployed to the cloud with one click without additional adaptation of cloud functions or login to the console.
  • Support for deploying traditional development framework applications (e.g. Express, Next. Js, Flask, Laravel, etc.) as Serverless applications.
  • Debug the function code locally, or use remote development mode to view and debug the log output of the deployment service locally in real time.
  • All infrastructure configuration (such as API gateway, COS storage, DB link, etc.) can be completed through simple configuration.
  • Quickly switch application deployment environment (development, demo, production), region.
  • You can easily learn about the application status, view logs, and error statistics.

03. Multifunction development examples

This example uses the Multi-scF and PostgreSQL components of the Serverless Framework to implement the following three apis.

  • GET /todos/Get all toDo items
  • POST /todos/Create a new ToDo item
  • POST /todos/{id}/actions/completeComplete toDo items

The Invoke and Logs functions provided by the Serverless Framework are used for debugging and viewing production environment real-time logs.

The code for this example is available in the Git repository.

Step 1: Install the Serverless Framework

Run the following command to install Serverless Framework

$ npm install serverless -g
Copy the code

If you have already installed the Serverless Framework, you can run the following command to upgrade to the latest version:

$ npm update serverless -g
Copy the code

This command will install the latest Serverless Framework to your computer. After the installation is successful, you can start using the Serverless Framework using Serverless or SLS

Step 2: Initialize the multi-function project

$ sls init multi-scf-nodejs --name sls-demo-msn-todo
Copy the code

In this command, the application template multi-scf-nodejs is used as the application directory of my-multi-scf-demo. After the initialization, the directory structure is

.├ ── readme.md ├── index.js ├─ key.ymlCopy the code

Here are the files for the following purposes:

  • Index. js: function file.
  • Serverless. yml: Serverless Framework configuration file.
    • App: The name of an application, which serves as the unique identifier of the application.
    • Stage: application environment. Different application instances can be deployed in different environments.
    • Component: Component name
    • Name: component instance name
    • Inputs: Component deployment input parameters

Step 3: Link to the database

Because Serverless is stateless (it is destroyed when run), you need to link to the database to persist toDO information. Before adding a database, you need to connect to the VPC network.

1. Add the VPC

Create a subdirectory VPC and add a serverless. Yml file to the subdirectory as follows:

component: vpc # [for] want to use components, see https://github.com/serverless-components for more components
name: sls-demo-msn-vpc # [Mandatory] Component instance name

inputs:
  region: ap-guangzhou # Locale where the instance belongs
  zone: ap-guangzhou-2 # Region of the instance
  vpcName: ${name} # Instance name, where name is used as the name.
  subnetName: sls-demo-msn-subnet # Name of the subnet
Copy the code

For details about VPC configurations, see VPC Private Networks.

In the configuration file of the child component, the app name automatically inherits the configuration in the parent directory serverless.yml. The name of an application must be the same.

2. Add a database

Create subdirectory db and add a new serverless.yml file to the subdirectory as follows:

component: postgresql #(required) The name of the reference component, currently using the PostgresQL component
name: sls-demo-msn-DB # (Required) The name of the instance created by this PostgresQL component

inputs:
  region: ap-guangzhou # Locale where the instance belongs
  zone: ap-guangzhou-2 # Region of the instance
  dBInstanceName: ${name}-${stage} The database instance name is unique, and one database can only exist in one VPC.
  extranetAccess: true Whether to enable real exception network access
  vpcConfig: VPC network configuration
    vpcId: ${output:${stage}:${app}:sls-demo-msn-vpc.vpcId} # Private network Id
    subnetId: ${output:${stage}:${app}:sls-demo-msn-vpc.subnetId} Id # subnet
Copy the code

Add a database to the VPC network in the database configuration. The output variable is used to dynamically obtain the ID of the VPC.

For details about how to configure variables, see Serverless variables.

For more information about PostgreSQL configuration, see the PostgreSQL database.

After the component deployment is complete, you can use SLS Info to view the output variables of the component in the component directory or view related information in the Application console of Tencent Cloud.

3. Initialize the application directory

  1. Creating a subdirectorysrcAnd will create the generatedindex.js(rename totodos.js) andserverless.ymlMove to a directory.
  2. insrcDirectory executionnpm initInitialize the node.js project.
  3. insrcDirectory executionnpm i pg --saveInstall database link dependency packagespg.
  4. Add a root configuration file to the project root directoryserverless.yml, the file is as follows:
app: sls-demo-msn-todo-3e5a2134 # Apply a unique identifier, which must be unique under the same account.
stage: dev The name of the application deployment environment, which uses the value of the environment variable STAGE.
Copy the code

The configuration file information in the root directory is inherited by the component and does not need to be duplicated in the child component. (Only for app and stage).

The final completed project directory structure is as follows:

. ├ ─ ─ the README. Md ├ ─ ─ the db # database │ └ ─ ─ serverless. Yml # database configuration file ├ ─ ─ serverless. Yml ├ ─ ─ the SRC # function application more │ ├ ─ ─ node_modules │ ├ ─ ─ │ ├── serverless. Yml │ ├── serverless. Yml │ ├── todos.js # VPC ├ ─ sci.pdfCopy the code

4. Modify the multi-function application configuration

Modify the configuration file in the multi-function directory SRC as follows:

component: multi-scf
name: sls-demo-msn

inputs:
  src:
    src: . /
    exclude:
      - .env
      - "node_modules/**" Ignore all files in node_modules directory to speed up deployment
  environments: # Apply environment variable information
    - key: PG_CONNECT_STRING
      value: ${output:${stage}:${app}:sls-demo-msn-DB.private.connectionString}
  region: ap-guangzhou
  runtime: Nodejs12.16
  memorySize: 128
  vpc: VPC network configuration
    vpcId: ${output:${stage}:${app}:sls-demo-msn-vpc.vpcId} # Private network Id
    subnetId: ${output:${stage}:${app}:sls-demo-msn-vpc.subnetId} Id # subnet
  installDependency: true Install dependencies online
  timeout: 6 # Default timeout (s)
  functions: # Multiple function definitions
    allTodo: # Function alias
      handler: todos.all # Processing function
      memorySize: 256 # Custom function memory space
    addTodo:
      handler: todos.add
      timeout: 9 # Customizes the timeout of this function in seconds
    completeTodo:
      handler: todos.comp
      timeout: 9
  triggers: # Trigger configuration
    - type: apigw
      parameters:
        name: todosAPIGW
        protocols:
          - https
          - http
        apis: # API configuration
          - path: /todos/ # Routing path
            method: GET # Routing method
            function: allTodo # Route handler alias
          - path: /todos/
            method: POST
            function: addTodo
          - path: /todos/{id}/actions/complete
            method: POST
            function: completeTodo
            param: Configure dynamic route parameters
              - name: id
                position: PATH
                required: true
                type: number
                desc: Todo ID
Copy the code

The main contents of modification are as follows:

  • useinstallDependencyAfter the deployment is enabled, automatic installation is dependent and ignorednode_moduleAll files in the directory (no need to upload node_modules to speed up deployment)
  • usevpcAdd a VPC network and connect it to the same VPC network.
  • useenvironmentsAdd the project environment variables and use the output variables to dynamically generate the database connection string.
  • usefunctionsTo declare functions and their aliases in a project.
  • usetriggersDeclare the function of the trigger and in the trigger’sapisTo configure the paths and parameters corresponding to each function.

For more configuration and details on function development, see the PostgreSQL database for more details.

For more descriptions of function development, see Function Development for more details.

Step 4: Develop functionality

Modify todos.js and complete the development of related functions. The final code of the file is as follows:

"use strict";
const { Client } = require("pg");

const client = new Client({
  connectionString: process.env.PG_CONNECT_STRING,
});

/** * Initialize database and table structure */
const initDB = async() = > {const isConnected = client && client._connected;

  if(! isConnected) {await client.connect();

    await client.query(` CREATE TABLE IF NOT EXISTS todo ( ID SERIAL NOT NULL, TITLE VARCHAR NOT NULL, NOTE TEXT, IS_COMPLETE BOOLEAN DEFAULT FALSE ); `); }};/** * Get all Todo items */
exports.all = async (event, context) => {
  // Async needs to turn off the event loop waiting to avoid problems with logging times out or functions not returning.
  context.callbackWaitsForEmptyEventLoop = false;
  await initDB();

  const { rows } = await client.query({ text: "SELECT * FROM todo" });

  return {
    message: "Tencent SCF execute successful!".data: rows,
  };
};

/** * Add new Todo items */
exports.add = async (event, context) => {
  // Async needs to turn off the event loop waiting to avoid problems with logging times out or functions not returning.
  context.callbackWaitsForEmptyEventLoop = false;
  const { title, note } = JSON.parse(event.body);
  if(! title) {return {
      statusCode: 400.message: "Missing Todo Title"}; }await initDB();
  const { rowCount } = await client.query({
    text: "INSERT INTO todo (title, note) VALUES($1, $2)".values: [title, note],
  });

  return rowCount === 1
    ? {
        statusCode: 201.message: "Todo added success.",}, {statusCode: 400.message: "Todo added failed."}; };/** * Complete the specified Todo */
exports.comp = async (event, context) => {
  // Async needs to turn off the event loop waiting to avoid problems with logging times out or functions not returning.
  context.callbackWaitsForEmptyEventLoop = false;
  const todoId = event.pathParameters.id;

  if(! todoId && !isNaN(todoId)) {
    return {
      statusCode: 400.message: "Missing Todo Id"}; }await initDB();
  const { rowCount } = await client.query({
    text: "UPDATE todo SET is_complete = true WHERE id=$1".values: [todoId],
  });

  return rowCount === 1
    ? {
        statusCode: 200.message: "Todo Complete success.",}, {statusCode: 400.message: "Todo Complete failed."}; };Copy the code

Step 5: Debug functions

1. Invoke debugging

In addition to using third-party development tools to debug code through configured API gateway URLS, you can also use the Serverless Framework’s Invoke functionality or remote debugging capabilities. The Invoke functionality is used here to demonstrate how to debug function functionality.

The Invoke and remote debugging functions need to be executed within the component’s directory.

2. Get all toDos

Do it in the SRC directory

$ serverless invoke -f allTodo
Copy the code

The result that can be obtained after execution

Use authorization information. In default authorization, if you need to use a temporary key, use --login to login again. BillDuration: 36 duration: 36 errMsg: functionRequestId: fe6d302d-f6db-42ad-9c7b-8d0c61ead9b3 invokeResult: 0log:
  """ START RequestId: fe6d302d-f6db-42ad-9c7b-8d0c61ead9b3 Event RequestId: fe6d302d-f6db-42ad-9c7b-8d0c61ead9b3 END RequestId: fe6d302d-f6db-42ad-9c7b-8d0c61ead9b3 Report RequestId: Fe6d302d-f6db-42ad-9c7b-8d0c61ead9b3 Duration:36ms Memory:256MB MemUsage:11.3984MB"""MemUsage: 11952128 -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- Serverless: {call success message:'Tencent SCF execute successful! ',
  data: []
}
Copy the code

The result returned by Invoke contains meta information such as elapsed time, errors, RequestId, execution logs, and the result returned by the function.

Create a new Todo

Do it in the SRC directory

$  serverless invoke -f addTodo --data "{\"body\":\"{\\\"title\\\":\\\"Create multi-scf project demo\\\",\\\"note\\\":\\\"Todo App with postgreSQL\\\"}\"}"
Copy the code

The result that can be obtained after execution

Use authorization information in default authorization, if you need to use a temporary key, use --login to login again billDuration: 35 duration: 35 errMsg: functionRequestId: 93f50016-064f-468d-9e98-31645fc254fd invokeResult: 0 log: """ START RequestId: 93f50016-064f-468d-9e98-31645fc254fd Event RequestId: 93f50016-064f-468d-9e98-31645fc254fd END RequestId: 93f50016-064f-468d-9e98-31645fc254fd Report RequestId: 93f50016-064F-468D-9e98-31645fc254fd Duration:35ms Memory:128MB MemUsage:11.293MB """ MemUsage: 11841536 -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- Serverless: call succeeds {statusCode: 201, the message: 'Todo added success.' }Copy the code

Step 6: Deployment and logging

1. Deploy code to the production environment

Use the following command to rapidly deploy a project to a production environment (named prod here)

$ serverless deploy --stage prod
Copy the code

2. View production environment logs in real time

Run the following command in the project directory SRC to view the instant log information of the project

$ sls logs --tail -f allTodo --stage prod
Copy the code

Here is the result:

Use authorization information default in authorization, if you need to use a temporary key, use --login to login again serverless ⚡components Action: "logs" -stage: "prod" -app: "sls-demo-msn-todo-3e5a2134" - Name: "sls-demo-msn" START RequestId:6f31857109130f092c547337c073ea91 Response RequestId:dbb3a8ed63a32be8e6b7a2dd8a32bbe2 RetMsg:{"message":"Tencent SCF execute successful!" ,"data":[{"id":1,"title":"Create multi-scf project demo","note":"Todo App with postgreSQL","is_complete":false}]} END RequestId:dbb3a8ed63a32be8e6b7a2dd8a32bbe2 Report RequestId:dbb3a8ed63a32be8e6b7a2dd8a32bbe2 Duration:4ms Memory:256MB MemUsage: 12.113281 MB Response RequestId: 485 a87cfc6ad385b7e9c84343962391b RetMsg: {" message ":" Tencent SCF execute successful!" ,"data":[{"id":1,"title":"Create multi-scf project demo","note":"Todo App with postgreSQL","is_complete":false}]} END RequestId:485a87cfc6ad385b7e9c84343962391b Report RequestId:485a87cfc6ad385b7e9c84343962391b Duration:4ms Memory:256MB MemUsage: 11.886719 MB START RequestId: 0 ede6d26dca55362a701c10ff51c9021 Serverless holds the listening...Copy the code

conclusion

Thanks to the vast number of developers who have been supporting Serverless Framework for a long time. In the future, we will continue to iterate the product, introduce new features, and improve the product use experience. Finally, we will build a complete solution for Chinese developers to meet the habits of Chinese developers.

You are also welcome to share your experiences and thoughts and feedback on the Serverless Chinese community.

Serverless Chinese community: github.com/serverless/…

Last hope everyone can participate in our sweepstakes questionnaire: www.surveymonkey.com/r/blog-msnt…

One More Thing

Experience Tencent Cloud Serverless Demo and receive the New User package 👉 Tencent Cloud Serverless Novice Experience

Welcome to: Serverless Chinese!