ESP32 - WEB サービス プログラムの移植 (restful_server の例に基づく)

1. はじめに

ESP32-WEB サービス プログラム テストプロジェクトを既存のプロジェクトに移植します。これには、固定 IP に基づく WIFI 接続、OTA アップグレード、WebSocket およびその他の機能が含まれます。

2. 移植

2.1 プロジェクトのパーティションを変更するには、restful_server プロジェクトの下のパーティション テーブル ファイル Partitions_example.csv を参照してください。

このモジュールはESP32-WROVER-E(4MB)を使用しているため、パーティションテーブルの内容を以下のように変更します(問題は後で判明します。後述します)。

# 名前、タイプ、サブタイプ、オフセット、サイズ、フラグ
nvs、データ、nvs、0x9000、0x4000 
otadata、データ、ota、0xd000、0x2000 
phy_init、データ、phy、0xf000、0x1000 
ota_0、app、ota_0、0x10000、1M 
ota_1、アプリ、ota_1、 、1M 
www、データ、スピフ、 、1M

そして、以下の図に示すように構成を変更します。

2.2 フロントエンドコードをコピーする

restful_server プロジェクトのフロント ディレクトリとそのすべての内容を既存のプロジェクトのルート ディレクトリにコピーします。

2.3rest_server.c ファイルを既存のプロジェクトのメイン ディレクトリにコピーします。

そして、メインディレクトリの CMakeLists.txt ファイルに「rest_server.c」を追加します。

idf_component_register(SRCS "ota.c" "wifi.c" "websocket.c" "rest_server.c" "main.c"
                    INCLUDE_DIRS "."
                    # Embed the server root certificate into the final binary
                    EMBED_TXTFILES ${project_dir}/server_certs/ca_cert.pem)

2.4 esp_rest_main.c ファイル内の次の内容を既存のプロジェクト main.c ファイルにコピーします。

//此处略去了必要的头文件和变量定义

esp_err_t start_rest_server(const char *base_path);

#if CONFIG_EXAMPLE_WEB_DEPLOY_SF
esp_err_t init_fs(void)
{
    esp_vfs_spiffs_conf_t conf = {
        .base_path = CONFIG_EXAMPLE_WEB_MOUNT_POINT,
        .partition_label = NULL,
        .max_files = 5,
        .format_if_mount_failed = false
    };
    esp_err_t ret = esp_vfs_spiffs_register(&conf);

    if (ret != ESP_OK) {
        if (ret == ESP_FAIL) {
            ESP_LOGE(TAG, "Failed to mount or format filesystem");
        } else if (ret == ESP_ERR_NOT_FOUND) {
            ESP_LOGE(TAG, "Failed to find SPIFFS partition");
        } else {
            ESP_LOGE(TAG, "Failed to initialize SPIFFS (%s)", esp_err_to_name(ret));
        }
        return ESP_FAIL;
    }

    size_t total = 0, used = 0;
    ret = esp_spiffs_info(NULL, &total, &used);
    if (ret != ESP_OK) {
        ESP_LOGE(TAG, "Failed to get SPIFFS partition information (%s)", esp_err_to_name(ret));
    } else {
        ESP_LOGI(TAG, "Partition size: total: %d, used: %d", total, used);
    }
    return ESP_OK;
}
#endif

void app_main(void)
{
    esp_err_t err = nvs_flash_init();
    if (err == ESP_ERR_NVS_NO_FREE_PAGES || err == ESP_ERR_NVS_NEW_VERSION_FOUND) {
        ESP_ERROR_CHECK(nvs_flash_erase());
        err = nvs_flash_init();
    }
    ESP_ERROR_CHECK( err );

    IO_Init();  
    ip_set();
    wifi_init_sta();
    xTaskCreate(&advanced_ota_example_task, "advanced_ota_example_task", 1024 * 8, service_ip, 5, NULL);
    websocket_app_start(service_ip);
    ESP_ERROR_CHECK(init_fs());
    ESP_ERROR_CHECK(start_rest_server(CONFIG_EXAMPLE_WEB_MOUNT_POINT));
    // tasklist_show();   
    while (1)
    {
        LED_Run();
        Key_Read();
        vTaskDelay(100 / portTICK_PERIOD_MS);
    }    
}

2.5 メインディレクトリの Kconfig.projbuild 内の次の内容を既存プロジェクトの対応するファイルにコピーします。

注: プロジェクト Kconfig.projbuild 内の元のコンテンツは、実際には使用されないため削除されます。

menu "Example Configuration"

    config EXAMPLE_MDNS_HOST_NAME
        string "mDNS Host Name"
        default "esp-home"
        help
            Specify the domain name used in the mDNS service.
            Note that webpage also take it as a part of URL where it will send GET/POST requests to.

    choice EXAMPLE_WEB_DEPLOY_MODE
        prompt "Website deploy mode"
        default EXAMPLE_WEB_DEPLOY_SEMIHOST
        help
            Select website deploy mode.
            You can deploy website to host, and ESP32 will retrieve them in a semihost way (JTAG is needed).
            You can deploy website to SD card or SPI flash, and ESP32 will retrieve them via SDIO/SPI interface.
            Detailed operation steps are listed in the example README file.
        config EXAMPLE_WEB_DEPLOY_SEMIHOST
            bool "Deploy website to host (JTAG is needed)"
            help
                Deploy website to host.
                It is recommended to choose this mode during developing.
        config EXAMPLE_WEB_DEPLOY_SD
            depends on IDF_TARGET_ESP32
            bool "Deploy website to SD card"
            help
                Deploy website to SD card.
                Choose this production mode if the size of website is too large (bigger than 2MB).
        config EXAMPLE_WEB_DEPLOY_SF
            bool "Deploy website to SPI Nor Flash"
            help
                Deploy website to SPI Nor Flash.
                Choose this production mode if the size of website is small (less than 2MB).
    endchoice

    if EXAMPLE_WEB_DEPLOY_SEMIHOST
        config EXAMPLE_HOST_PATH_TO_MOUNT
            string "Host path to mount (e.g. absolute path to web dist directory)"
            default "PATH-TO-WEB-DIST_DIR"
            help
                When using semihost in ESP32, you should specify the host path which will be mounted to VFS.
                Note that only absolute path is acceptable.
    endif

    config EXAMPLE_WEB_MOUNT_POINT
        string "Website mount point in VFS"
        default "/www"
        help
            Specify the mount point in VFS.

endmenu

保存後、再度設定を開くと以下のオプションが表示されるので、以下の設定を行います。

2.6 メインディレクトリの CMakeLists.txt の次の内容を既存プロジェクトの対応するファイルにコピーします。

if(CONFIG_EXAMPLE_WEB_DEPLOY_SF)
    set(WEB_SRC_DIR "${CMAKE_CURRENT_SOURCE_DIR}/../front/web-demo")
    if(EXISTS ${WEB_SRC_DIR}/dist)
        spiffs_create_partition_image(www ${WEB_SRC_DIR}/dist FLASH_IN_PROJECT)
    else()
        message(FATAL_ERROR "${WEB_SRC_DIR}/dist doesn't exit. Please run 'npm run build' in ${WEB_SRC_DIR}")
    endif()
endif()

2.7 ルート ディレクトリの Makefilet にある次の内容を、既存のプロジェクトの対応するファイルにコピーします。

ifdef CONFIG_EXAMPLE_WEB_DEPLOY_SF
WEB_SRC_DIR = $(shell pwd)/front/web-demo
ifneq ($(wildcard $(WEB_SRC_DIR)/dist/.*),)
SPIFFS_IMAGE_FLASH_IN_PROJECT := 1
$(eval $(call spiffs_create_partition_image,www,$(WEB_SRC_DIR)/dist))
else
$(error $(WEB_SRC_DIR)/dist doesn't exist. Please run 'npm run build' in $(WEB_SRC_DIR))
endif
endif

2.8 次のように構成を変更します。

   

ここでファイル名の長さが短すぎると、プロジェクトのコンパイル時にエラーが報告されます(フロントエンド部分によって生成されるファイル名は比較的長いです)。

3. デバッグ

プロジェクトの変更が完了した後、コンパイル時に次のエラーが発生します

 

 その後、フロントエンドによって生成された dist ディレクトリの内容が 1M を超える記憶領域を占有していたことが判明しましたが、パーティション サイズを調整した後は正常でした。

おすすめ

転載: blog.csdn.net/tsliuch/article/details/128158286