SQL Server Linux的Docker容器不断退出

时间:2017-05-21 01:16:02

标签: sql-server linux docker dockerfile

我想通过在容器启动时添加一个包含一个表的简单数据库来修改SQL Server Linux的容器行为。

我看到此问题的泊坞窗图片版本是截至2017年5月20日的最新版本,即ctp2-1

我在Docker for Windows使用17.05.0-ce最新版本。我将MobyLinuxVM的RAM增加到6144MB,因为建议使用超过4GB。

重现问题的步骤

准备文件

(1) Create a local Windows folder, in my case, 

    C:\temp\docker\

(2) Add "Dockerfile" (note no file extension) with the following content.

    FROM microsoft/mssql-server-linux:latest
    COPY ./custom /tmp
    RUN chmod +x /tmp/entrypoint.sh \
        && chmod +x /tmp/createdb.sh
    CMD /bin/bash /tmp/entrypoint.sh

(3) Add a subfolder "custom"

    C:\temp\docker\custom\

(4) Add 3 files to "custom" subfolder with following content.

   (A) entrypoint.sh
    /opt/mssql/bin/sqlservr & /tmp/createdb.sh

   (B) createdb.sh
    sleep 30s
    /opt/mssql-tools/bin/sqlcmd -S localhost -U sa -P '!StrongPass45' -d master -i /tmp/createdb.sql

   (C) createdb.sql
    CREATE DATABASE DemoData;
    GO
    USE DemoData;
    GO
    CREATE TABLE Products (ID int, ProductName nvarchar(max));
    GO

运行DOCKER命令(你将在这里看到最后一步的问题)

(1) Open PowerShell and cd to folder in step (1) above, in my case

    cd C:\temp\docker

(2) Run docker build command

    docker build .

(3) After image is built, run the following command and remember the first 3 letters of your image id, in my case "e65"

    docker images

    [![enter image description here][2]][2]

(4) Create the container with the following command (note the last 3 characters should be replaced by yours, also use the same password you used above)

    docker run -d -e SA_PASSWORD="!StrongPass45" -e ACCEPT_EULA="Y" -p 1433:1433 e65

(5) Check your container is running

    docker ps -a

  [![enter image description here][2]][2]

(6) Wait about 2 minutes and check your container status again. AT THIS POINT, THE CONTAINER WOULD HAVE EXITED.

   docker ps -a

   [![enter image description here][2]][2]

我按如下方式检查了日志。

docker logs e65

在SQL Server成功创建DemoData数据库之后,下面是日志的底部。

[![enter image description here][2]][2]

IMO,日志中的问题就是这一个

Parallel redo is shutdown for database 'DemoData' with worker pool size [1].

我已尝试过各种其他SQL语句(甚至添加自定义MDF和LDF文件并附加到它们)以向OOB映像添加行为。 我甚至可以在容器退出之前使用SSMS连接到新数据库几秒钟!

有没有人见过这个问题?有人可以尝试一下吗?

1 个答案:

答案 0 :(得分:2)

有效的解决方案

根据我收到的反馈,很明显Dockerfile中的CMD正在返回。以下是解决问题的完整步骤。

[如果您找到了一个更可靠的解决方案,请告诉我,该解决方案不依赖于我在此解决方案中编写的某个超时值,以允许SQL Server在容器启动时自行引导]

预付文件

(1)创建一个本地Windows文件夹,在我的例子中,

C:\temp\docker\

(2)添加" Dockerfile" (注意没有文件扩展名),内容如下。

FROM microsoft/mssql-server-linux:latest
COPY ./custom /tmp
RUN chmod +x /tmp/entrypoint.sh
CMD /bin/bash /tmp/entrypoint.sh

(3)添加子文件夹" custom"

C:\temp\docker\custom\

(4)将2个文件添加到" custom"子文件夹如下。

entrypoint.sh

#!/bin/bash

set -e
run_cmd="/opt/mssql-tools/bin/sqlcmd -S localhost -U sa -P HdkPKD57%@6876^ -l 30 -d master -i /tmp/createdb.sql"

>&2 echo "Allowing 30 seconds for SQL Server to bootstrap, then creating database.."
until $run_cmd & /opt/mssql/bin/sqlservr; do
>&2 echo "This should not be executing!"
done

createdb.sql

CREATE DATABASE DemoData;
GO
USE DemoData;
GO
CREATE TABLE Products (ID int, ProductName nvarchar(max));
GO

运行DOCKER命令

(A)在上面的步骤(1)中打开PowerShell和cd到文件夹,在我的情况下

cd C:\temp\docker

(B)运行docker build命令

docker build .

(C)构建图像后,获取图像的前3个字符,在我的情况下086

docker images

docker image

(D)使用正确的图像ID和正确的密码

创建容器
docker run -d -e 'SA_PASSWORD=HdkPKD57%@6876^' -e 'ACCEPT_EULA=Y' -p 1433:1433 086

(E)检查您的容器是否正在运行

docker ps -a

container

此容器不会退出!预期的数据库" DemoData"被建造。问题解决了!

docker logs 2aa命令(2aa是我的容器ID,你的将是不同的)显示干净的构建,没有错误或警告。日志开始如下

Allowing 30 seconds for SQL Server to bootstrap, then creating database..
This is an evaluation version.  There are [173] days left in the evaluation period.
2017-05-21 17:39:50.69 Server      Setup step is copying system data file 'C:\templatedata\master.mdf' to '/var/opt/mssql/data/master.mdf'.
....

结束如下。

2017-05-21 17:39:54.20 spid51      Starting up database 'DemoData'.
2017-05-21 17:39:54.43 spid51      Parallel redo is started for database 'DemoData' with worker pool size [1].
2017-05-21 17:39:54.44 spid51      Parallel redo is shutdown for database 'DemoData' with worker pool size [1].
2017-05-21 17:39:54.51 spid7s      Recovery is complete. This is an informational message only. No user action is required.
Changed database context to 'DemoData'.

与SSMS联络

我能够使用SSMS成功连接到此数据库,如下所示(IP地址10.0.75.1是包含容器的docker主机的地址)

enter image description here

重要提示

  • sqlcmd SA密码

    sqlcmd是用于运行dbcreate.SQL并创建数据库DemoData的实用程序。该实用程序在Linux上使用ODBC驱动程序,并且对如何为交换机指定值敏感,尤其是密码-P

    要避免与登录相关的问题found hereexplained here,请仔细选择您的强密码,并在entrypoint.sh-P指定,但不要使用double quotes或{single quotes {1}}或[]。请参阅上面的(4)

    此外,此密码必须与您传递给容器的docker run环境变量相匹配。请参阅上面的(D)以避免密码不匹配。

    详细documentation on sqlcmd is here

  • sqlcmd登录超时

    请注意我如何使用-l开关为30 seconds文件中的sqlcmd指定entrypoint.sh的登录超时。这是我的解决方案的关键,以避免CMD返回(这使得容器退出)。此超时足够长,SQL Server可以启动。