

AWS 大型机现代化服务（托管运行时环境体验）不再向新客户开放。有关类似于 AWS 大型机现代化服务（托管运行时环境体验）的功能，请浏览 AWS 大型机现代化服务（自我管理体验）。现有客户可以继续正常使用该服务。有关更多信息，请参阅[AWS 大型机现代化可用性变更](https://docs.aws.amazon.com/m2/latest/userguide/mainframe-modernization-availability-change.html)。

本文属于机器翻译版本。若本译文内容与英语原文存在差异，则一律以英文原文为准。

# AWS 为大型机进行转型 Blusam
<a name="ba-shared-blusam"></a>

在大型机系统（以下主题中称为“遗留系统”）上，业务数据通常使用 VSAM（虚拟存储访问方法）存储。数据存储在“记录”（字节数组）中，属于“数据集”。

有四个数据集组织：
+ **KSDS**：按键排序的数据集：按主键（不支持重复的键）和可选的其他“备用”键为记录编制索引。所有键值都是记录字节数组的子集，每个键由以下内容定义：
  + 偏移量 [基于 0（0 是记录字节数组内容的开头），以字节为单位]
  + 长度（以字节为单位）
  + 是否支持重复的值
+ **ESDS**：按条目排序的数据集：记录主要按顺序访问（基于它们在数据集中的插入顺序），但可以使用其他备用键进行访问；
+ **RRDS**：相对记录数据集：使用“跳跃”访问记录，使用相对记录号；可以向前跳跃，也可以向后跳跃；
+ **LDS**：线性数据集：这里没有记录，只有一个按页组织的字节流。主要用于遗留平台上的内部用途。

在对传统应用程序进行现代化 AWS 改造时，使用 Transform for 大型机重构方法，现代化的应用程序不再打算访问 VSAM 存储的数据，同时保留数据访问逻辑。该Blusam组件就是答案：它允许从传统 VSAM 数据集导出中导入数据，为现代化应用程序提供操作它们的 API 以及专用的管理 Web 应用程序。请参阅[AWS 为大型机Blusam管理控制台进行转换](ba-shared-bac-userguide.md)。

**注意**  
Blusam仅支持 KSDS、ESDS 和 RRDS。

BlusamAPI 使保留数据访问逻辑（顺序、随机和相对读取；插入、更新和删除记录）成为可能，而组件架构依赖于缓存策略和基于 RDBMS 的存储的组合，允许在资源有限的情况下进行高吞吐量 I/O 操作。

## Blusam 基础设施
<a name="ba-shared-blusam-infrastructure"></a>

Blusam依赖 PostgreSQL RDBMS 存储数据集，包括原始记录数据和密钥索引（如果适用）。最喜欢的选择是使用兼容亚马逊 Aurora PostgreSQL 的引擎。本主题中的示例和插图均基于该引擎。

**注意**  
服务器启动时，Blusam运行时会检查是否存在一些必需的技术表，如果找不到这些表，则创建它们。因此，必须向配置中使用的访问Blusam数据库的角色授予创建、更新和删除数据库表（包括行和表定义本身）的权限。有关如何禁用的信息Blusam，请参阅[Blusam 配置](#ba-shared-blusam-configuration)。

### 缓存
<a name="ba-shared-blusam-caching"></a>

除了存储本身之外，当与缓存实现相结合时，Blusam运行速度更快。

目前支持两个缓存引擎， EhCache 以及 Redis，每个引擎都有自己的用例：
+ EhCache : 独立嵌入式易失性本地缓存 
  + **不**符合 AWS 大型机现代化托管环境部署的资格。
  + 通常在使用单个节点（例如单个 Apache Tomcat 服务器）运行现代化应用程序时使用。例如，该节点可能专用于托管批处理作业任务。
  + V@@ **ol** atile： EhCache 缓存实例是易失的；其内容将在服务器关闭时丢失。
  + **嵌入式**： EhCache 和服务器共享相同的 JVM 内存空间（在定义托管计算机规格时要考虑这个问题）。
+ Redis：共享永久缓存 
  + 有资格部署 AWS 大型机现代化托管环境。
  + 通常用于多节点情况，尤其是当多个服务器共用一个负载均衡器时。缓存内容在所有节点之间共享。
  + Redis 是永久性的，不受节点生命周期的约束。它在自己的专用计算机或服务（例如 Amazon ElastiCache）上运行。缓存对所有节点都是远程的。

### 锁定
<a name="ba-shared-blusam-locking"></a>

要处理对数据集和记录的并行访问，需要Blusam依靠可配置的锁定系统。锁定可以应用于两个级别：数据集和记录：
+ 针对写入目的锁定数据集将阻止所有其他客户端在任何级别（数据集或记录）对其执行写入操作。
+ 在记录级别针对写入进行锁定只会阻止其他客户端对给定记录执行写入操作。

应根据缓存配置相应地配置Blusam锁定系统：
+ 如果选择作为缓存实现， EhCache 则无需进行进一步的锁定配置，因为应使用默认的内存中锁定系统。
+ 如果选择 Redis 作为缓存实现，则需要进行基于 Redis 的锁定配置，以支持从多个节点进行并发访问。用于锁的 Redis 缓存不必与用于数据集的 Redis 缓存相同。有关配置基于 Redis 的锁定系统的信息，请参见 [Blusam 配置](#ba-shared-blusam-configuration)。

## Blusam内在函数和从旧版迁移数据
<a name="ba-shared-blusam-intrinsics"></a>



### 存储数据集：记录和索引
<a name="ba-shared-blusam-storage"></a>

每个传统数据集在导入到Blusam后都将存储到一个专用表中；该表的每一行使用两列代表一条记录：
+ 数字 ID 列，大整数类型，即表的主键，用于存储记录的相对字节地址（RBA）。RBA 表示自数据集开头的偏移量（以字节为单位），从 0 开始。
+ 字节数组记录列，用于存储原始记录的内容。

例如，请参阅 CardDemo 应用程序中使用的 KSDS 数据集的内容：

![查询结果显示值为 0 到 3600 的 id 列和包含二进制数据的记录列。](http://docs.aws.amazon.com/zh_cn/m2/latest/userguide/images/sample_dataset_storage.png)

+ 这个特定的数据集包含固定长度的记录，长度为 300 字节（因此 id 的集合是 300 的倍数）。
+ 默认情况下，用于查询 PostgreSQL 数据库的 pgadmin 工具不显示字节数组列内容，而是打印 [二进制数据] 标签。
+ 原始记录内容与从遗留平台导出的原始数据集相匹配，无需进行任何转换。特别是，不会发生字符集转换；这意味着记录的字母数字部分必须由使用遗留字符集（很可能是 EBCDIC 变体）的现代化应用程序进行解码。

关于数据集元数据和键索引：每个数据集都与名为 `metadata` 的表中的两行相关联。这是默认的命名约定。若要了解如何对其进行自定义，请参阅 [Blusam 配置](#ba-shared-blusam-configuration)。

![该表显示了两行，其中包含 VSAM KSDS 数据集条目的名称和元数据列。](http://docs.aws.amazon.com/zh_cn/m2/latest/userguide/images/sample_dataset_metadata_rows.png)

+ 第一行将数据集名称作为 *name* 列的值。*metadata* 列是一个二进制列，其中包含给定数据集的一般元数据的二进制序列化。有关更多信息，请参阅 [常规数据集元数据属性](#ba-shared-blusam-metadata)。
+ 第二行将数据集名称加上 `__internal'` 后缀作为 *name* 列的值。*metadata* 列的二进制内容取决于数据集的“大小”。
  + 对于 small/medium 数据集，内容是以下内容的压缩序列化：
    + 数据集使用的键的定义；主键定义（对于 KSDS）和备用键定义（如果适用）（对于 KSDS/ESDS）
    + 键索引（如果适用）（带有备用键定义的 KSDS/ESDS）：用于记录的索引浏览；键索引将键值映射到记录的 RBA；
    + 记录长度映射：用于记录的顺序/相对浏览；
  + 对于 Large/Very 大型数据集，内容是以下内容的压缩序列化：
    + 数据集使用的键的定义；主键定义（对于 KSDS）和备用键定义（如果适用）（对于 KSDS/ESDS）

此外， large/very 大型数据集索引（如果适用）使用分页机制存储；索引页的二进制序列化存储为专用表的行（每个数据集键一个表）。每个索引页存储在一行中，其中包含以下几列：
+ id：索引页的技术标识符（数字主键）；
+ firstkey：存储在索引页中的第一个（最低）键值的二进制值；
+ lastkey：存储在索引页中的最后一个（最高）键值的二进制值；
+ metadata：索引页的二进制压缩序列化（将键值映射到记录 RBAs）。

![数据库表显示 id、firstkey bytea、lastkey bytea 和带有二进制数据行的元数据 oid 的列。](http://docs.aws.amazon.com/zh_cn/m2/latest/userguide/images/sample_index_pages.png)


表名称是数据集名称和键内部名称的串联，键内部名称包含键的相关信息，例如键偏移量、键是否接受重复项（设置为 true 将支持重复项）以及键长度。例如，假设一个名为 “AWS\_LARGE\_KSDS” 的数据集具有以下两个已定义的密钥：
+ 主键 [偏移量：0，重复项：false，长度：18]
+ 备用键 [偏移量：3，重复项：true，长度：6]

在本例中，下表存储了与这两个键相关的索引。

![两个折叠的表格条目标记为 aws_large_ksds_0f18 和 aws_large_ksds_3f6。](http://docs.aws.amazon.com/zh_cn/m2/latest/userguide/images/sample_large_dataset_indexes_tables.png)


### 使用写入 I/O 机制优化吞吐量
<a name="ba-shared-blusam-write-behind"></a>

为了优化插入/更新/删除操作的性能，该Blusam引擎依赖于可配置的写入机制。该机制建立在一个专用线程池之上，这些线程使用批量更新查询处理持久性操作，以最大限度地提高Blusam存储 I/O 吞吐量。

该Blusam引擎收集应用程序对记录执行的所有更新操作，并生成发送到专用线程进行处理的记录批次。然后，使用批量更新查询将这些批次持久化到Blusam存储中，避免使用原子持久性操作，从而确保网络带宽得到最佳利用。

该机制使用可配置的延迟（默认为一秒）和可配置的批大小（默认为 10000 条记录）。只要满足以下两个条件中的第一个，就会立即执行构建持久性查询：
+ 配置的延迟已过且批不为空
+ 批中要处理的记录数达到配置的限制

若要了解如何配置回写机制，请参阅[可选属性](#ba-shared-blusam-configuration-engine-optional-properties)。

### 选择合适的存储方案
<a name="ba-shared-blusam-storage-scheme"></a>

如上一节所述，数据集的存储方式取决于它们的“大小”。但是对于一个数据集而言，什么是小、中、大呢？ 何时应该选择分页存储策略而不是常规存储策略？

该问题的答案取决于以下几点。
+ 托管将使用这些数据集的现代化应用程序的每个服务器上的可用内存容量。
+ 缓存基础设施（如果有）上的可用内存容量。

使用非分页索引存储方案时，每个数据集的完整键索引和记录大小信息集合都会在数据集打开时加载到服务器内存中。此外，如果涉及缓存，则可能会使用常规方法将所有数据集记录预加载到缓存中，这可能会导致缓存基础设施端的内存资源耗尽。

根据定义的键的数量、键值的长度、记录数量和同时打开的数据集数量，可以粗略地估算出给定的已知用例将消耗的内存容量。

要了解更多信息，请参阅[估算给定数据集的内存占用](#ba-shared-blusam-memory)。

### Blusam 迁移
<a name="ba-shared-blusam-migration"></a>

为给定数据集选择了正确的存储方案后，必须通过迁移传统数据集来填充Blusam存储空间。

为此，必须使用遗留数据集的**原始二进制导出**，在导出过程中不使用任何字符集转换。从遗留系统传输数据集导出时，请确保不要破坏二进制格式。例如，使用 FTP 时强制使用二进制模式。

**原始二进制导出**仅包含记录。导入机制不需要导 keys/indexes 出，因为所有导出 keys/indexes 都是通过导入机制即时重新计算的。

数据集二进制导出可用后，有几种方法可以将其迁移到Blusam存在：

在 AWS 大型机现代化托管环境中：
+ 使用专用特征导入数据集。请参阅[为 AWS Mainframe Modernization 应用程序导入数据集](applications-m2-dataset.md)。

或者
+ 使用数据集批量导入工具。请参阅 [AWS 大型机现代化数据集定义参考](datasets-m2-definition.md)和[VSAM 数据集请求格式示例](datasets-m2-definition.md#datasets-m2-definition-vsam)。

或者
+ 利用专用的加载服务，使用 groovy 脚本导入数据集。

**注意**  
目前，只能使用 groovy 脚本在 Mainframe Modernization 托管环境中导入 LargeKSDS 和 LargeESDS。

在 Amazon EC2 上为大型机运行时进行 AWS 转换时：
+ 使用导入数据集[AWS 为大型机Blusam管理控制台进行转换](ba-shared-bac-userguide.md)。

或者
+ 利用专用的加载服务，使用 groovy 脚本导入数据集。

#### 使用 Groovy 脚本导入数据集
<a name="ba-shared-blusam-migration-groovy"></a>

本节将帮助您编写用于将旧数据集导入的groovy脚本。Blusam

首先要进行一些必需的导入：

```
import com.netfective.bluage.gapwalk.bluesam.BluesamManager
import com.netfective.bluage.gapwalk.bluesam.metadata.Key;
import com.netfective.bluage.gapwalk.rt.provider.ServiceRegistry
import java.util.ArrayList; //used for alternate keys if any
```

之后，对于要导入的每个数据集，根据给定的模式构建代码：

1. 创建或清除映射对象

1. 在映射中填充所需的属性（这因数据集类型而异，详见下文）

1. 在服务注册表中检索要用于数据集类型的适当加载服务

1. 使用映射作为参数运行服务

可以使用以下标识符从服务注册表中检索 5 种服务实现：
+ `"BluesamKSDSFileLoader"`: 适用于 small/medium 大小的 KSDS
+ `"BluesamESDSFileLoader"`适用于 small/medium 大小 ESDS
+ `"BluesamRRDSFileLoader"`：适用于 RRDS
+ `"BluesamLargeKSDSFileLoader"`：适用于大型 KSDS
+ `"BluesamLargeESDSFileLoader"`：适用于大型 ESDS

为 KSDS/ESDS 选择常规版还是大型版服务取决于数据集的大小以及要应用于数据集的存储策略。要了解如何选择适当的存储策略，请参阅[选择合适的存储方案](#ba-shared-blusam-storage-scheme)。

为了能够成功地将数据集导入Blusam，必须向加载服务提供正确的属性。

常用属性：
+ 必需（适用于所有类型的数据集）
  + “bluesamManager”：预期值为 `applicationContext.getBean(BluesamManager.class)`
  + “datasetName”：数据集名称，为字符串
  + “inFilePath"：旧数据集导出的路径，为字符串
  + “recordLength”：固定记录长度（对于可变记录长度数据集，为 0），为整数
+ 可选
  + **不支持大型数据集：**
    + “isAppend”：一个布尔标志，表示导入是在追加模式下进行的（将记录追加到现有Blusam数据集）。
    + “useCompression”：一个布尔标志，指示将使用压缩来存储元数据。
  + **仅适用于大型数据集：**
    + “indexingPageSizeInMb"：数据集的每个键的每个索引页的大小（以兆字节为单位），严格为正整数

依赖于数据集类型的属性：
+ KSDS/大型 KSDS：
  + 必需：
    + “primaryKey”：使用 `com.netfective.bluage.gapwalk.bluesam.metadata.Key` 构造函数调用构建的主键定义。
  + 可选：
    + “alternateKeys”：使用 `com.netfective.bluage.gapwalk.bluesam.metadata.Key` 构造函数调用构建的备用键定义列表（`java.util.List`）。
+ ESDS/大型 ESDS：
  + 可选：
    + “alternateKeys”：使用 `com.netfective.bluage.gapwalk.bluesam.metadata.Key` 构造函数调用构建的备用键定义列表（`java.util.List`）。
+ RRDS：
  + 无。

键构造函数调用：
+ `new Key(int offset, int length)`：创建一个键对象，该对象具有给定的键属性（偏移量和长度），并且不支持重复项。此变体应该用于定义主键。
+ `new Key(boolean allowDuplicates, int offset, int length)`：创建一个键对象，该对象具有给定的键属性（偏移量和长度），并带有支持重复项标志。

以下 Groovy 示例展示了各种加载场景。

加载具有两个备用键的大型 KSDS：

```
import com.netfective.bluage.gapwalk.bluesam.BluesamManager
import com.netfective.bluage.gapwalk.bluesam.metadata.Key;
import com.netfective.bluage.gapwalk.rt.provider.ServiceRegistry
import java.util.ArrayList;

// Loading a large KSDS into Blusam
def map = [:]
map.put("bluesamManager", applicationContext.getBean(BluesamManager.class));
map.put("datasetName", "largeKsdsSample");
map.put("inFilePath", "/work/samples/largeKsdsSampleExport");
map.put("recordLength", 49);
map.put("primaryKey", new Key(0, 18));
ArrayList altKeys = [new Key(true, 10, 8), new Key(false, 0, 9)]
map.put("alternateKeys", altKeys);
map.put("indexingPageSizeInMb", 25);
def service = ServiceRegistry.getService("BluesamLargeKSDSFileLoader");
service.runService(map);
```

加载没有备用键的可变记录长度 ESDS：

```
import com.netfective.bluage.gapwalk.bluesam.BluesamManager
import com.netfective.bluage.gapwalk.bluesam.metadata.Key;
import com.netfective.bluage.gapwalk.rt.provider.ServiceRegistry

// Loading an ESDS into Blusam
def map = [:]
map.put("bluesamManager", applicationContext.getBean(BluesamManager.class));
map.put("datasetName", "esdsSample");
map.put("inFilePath", "/work/samples/esdsSampleExport");
map.put("recordLength", 0);
def service = ServiceRegistry.getService("BluesamESDSFileLoader");
service.runService(map);
```

可变记录长度数据集导出将包含必需的记录描述字（RDW）信息，以支持在读取时对记录进行拆分。

加载固定记录长度 RRDS：

```
import com.netfective.bluage.gapwalk.bluesam.BluesamManager
import com.netfective.bluage.gapwalk.bluesam.metadata.Key;
import com.netfective.bluage.gapwalk.rt.provider.ServiceRegistry

// Loading a RRDS into Blusam
def map = [:]
map.put("bluesamManager", applicationContext.getBean(BluesamManager.class));
map.put("datasetName", "rrdsSample");
map.put("inFilePath", "/work/samples/rrdsSampleExport");
map.put("recordLength", 180);
def service = ServiceRegistry.getService("BluesamRRDSFileLoader");
service.runService(map);
```

在**多架构模式下**加载数据集：

**多架构模式**：在某些传统系统中，VSAM 文件被组织成文件集，允许程序访问和修改指定分区内的数据。现代系统将每个文件集视为一个架构，从而实现类似的数据分区和访问控制。

 要在`application-main.yml`文件中启用**多架构模式**，请参阅。[Blusam 配置](#ba-shared-blusam-configuration)在此模式下，可以使用共享上下文将数据集加载到特定架构中，共享上下文是用于存储运行时信息的内存注册表。要将数据集加载到特定架构中，请在数据集名称前加上相关的架构名称。

将 KSDS 文件加载到**多**架构模式的特定架构中：

```
import com.netfective.bluage.gapwalk.bluesam.BluesamManager
import com.netfective.bluage.gapwalk.bluesam.metadata.Key;
import com.netfective.bluage.gapwalk.rt.provider.ServiceRegistry
import java.util.ArrayList;
import com.netfective.bluage.gapwalk.rt.shared.SharedContext;

// Loading a KSDS into Blusam
def map = [:]
String schema = "schema1";
String datasetName = schema+"|"+"ksdsSample";
SharedContext.get().setCurrentBlusamSchema(schema);
schema = SharedContext.get().getCurrentBlusamSchema();
map.put("bluesamManager", applicationContext.getBean(BluesamManager.class));
map.put("datasetName", datasetName);
map.put("inFilePath", "/work/samples/ksdsSampleExport");
map.put("recordLength", 49);
map.put("primaryKey", new Key(0, 18));
map.put("indexingPageSizeInMb", 25);
def service = ServiceRegistry.getService("BluesamKSDSFileLoader");
service.runService(map);
```

将大型 KSDS 文件加载到**多架构模式的特定架构**中：

```
import com.netfective.bluage.gapwalk.bluesam.BluesamManager
import com.netfective.bluage.gapwalk.bluesam.metadata.Key;
import com.netfective.bluage.gapwalk.rt.provider.ServiceRegistry
import java.util.ArrayList;
import com.netfective.bluage.gapwalk.rt.shared.SharedContext;

// Loading a Large KSDS into Blusam
def map = [:]
String schema = "schema1";
String datasetName = schema+"|"+"largeKsdsSample";
SharedContext.get().setCurrentBlusamSchema(schema);
schema = SharedContext.get().getCurrentBlusamSchema();
map.put("bluesamManager", applicationContext.getBean(BluesamManager.class));
map.put("datasetName", datasetName);
map.put("inFilePath", "/work/samples/LargeKsdsSampleExport");
map.put("recordLength", 49);
map.put("primaryKey", new Key(0, 18));
map.put("indexingPageSizeInMb", 25);
def service = ServiceRegistry.getService("BluesamLargeKSDSFileLoader");
service.runService(map);
```

此外，还可使用配置条目（在`application-main.yml`配置文件中设置）来微调导入过程：
+ `bluesam.fileLoading.commitInterval`: 一个严格的正整数，定义常规ESDS/KSDS/RRDS导入机制的提交间隔。**不适用于大型数据集的导入。**默认值为 100000。

## Blusam 配置
<a name="ba-shared-blusam-configuration"></a>

配置Blusam发生在`application-main.yml`配置文件中（或Blusam管理控制台--BAC--应用程序的独立部署的`application-bac.yml`配置文件中）。

Blusam必须从两个方面进行配置：
+ Blusam存储和缓存访问配置
+ Blusam发动机配置

### Blusam存储和缓存访问配置
<a name="ba-shared-blusam-configuration-storage"></a>

有关如何使用密钥管理器或数据源配置对Blusam存储和缓存的访问权限的信息，请参阅。[为大型机运行时 AWS 转换设置配置](ba-runtime-config.md)

**注意**  
关于对Blusam存储的访问权限，使用的凭据将指向具有相应权限的连接角色。为了使Blusam引擎能够按预期运行，连接角色必须具有以下权限：
+ 连接到数据库
+ 创建/删除/更改/截断表和视图
+ 选择/插入/删除/更新表格和视图中的行
+ 执行函数或过程

### Blusam发动机配置
<a name="ba-shared-blusam-configuration-engine"></a>



#### 禁用 Blusam 支持
<a name="ba-shared-blusam-configuration-disabling"></a>

首先，让我们提一下，通过将`bluesam.disabled`属性设置为，可以完全禁用Blusam支持`true`。应用程序启动时，服务器日志中将显示一条信息消息，提醒您Blusam禁用：

```
BLUESAM is disabled. No operations allowed.
```

在这种情况下，无需进行进一步的配置，任何尝试使用Blusam相关功能（无论Blusam是以编程方式还是通过 REST 调用）都将引发 Java 代码执行`UnsupportedOperationException`中的问题，并附上有关Blusam被禁用的相关解释消息。

#### Blusam发动机属性
<a name="ba-shared-blusam-configuration-engine-properties"></a>

Blusam引擎配置属性在 bluesam key 前缀下重新分组：

##### 必需属性
<a name="ba-shared-blusam-configuration-engine-mandatory-properties"></a>


+ `cache`：将以所选择的缓存实现赋值。有效值为：
  + `ehcache`：使用本地嵌入式 ehcache。请参阅上面的相关用例限制。
  + `redis`：使用共享远程 redis 缓存。这是 AWS 大型机现代化托管用例的首选选项。
  + `none`：禁用存储缓存
+ `persistence`: 待用 pgsql 进行估值（PostgreSQL 引擎：最低版本 10.0 — 推荐版本 >=14.0
+ 数据源参考：`<persistence engine>.dataSource`将指向用于Blusam存储连接的 DataSource 定义，该定义在配置文件的其他地方定义。这通常被命名为 `bluesamDs`。

**注意**  
每当使用 Redis 作为缓存机制时，无论是用于数据还是锁（请见下文），都需要配置对 Redis 实例的访问权限。有关详细信息，请参阅 [大型机运行时 AWS 转换中可用的 Redis 缓存属性](ba-runtime-redis-configuration.md)。

##### 可选属性
<a name="ba-shared-blusam-configuration-engine-optional-properties"></a>

Blusam锁：属性前缀为 `locks`
+ `cache`: 唯一可用的值是`redis`，指定将使用基于 redis 的锁定机制（当Blusam存储缓存也基于 redis 时使用）。如果该属性缺失或未设置为 `redis`，则将使用默认的内存内锁定机制。
+ `lockTimeOut`：一个正的长整数值，用于指定尝试锁定已锁定的元素被标记为失败之前的超时时间（以毫秒为单位）。默认值为 `500`。
+ `locksDeadTime`：一个正的长整数值，表示应用程序可以持有锁的最长时间（以毫秒为单位）。在该时间过后，锁会自动标记为已过期并被释放。默认值为 `1000`；
+ `locksCheck`: 一个字符串，用于定义当前锁管理器使用的关于移除过期Blusam锁的锁定检查策略。将从以下值中选择：
  + `off`：不执行任何检查。不建议，因为可能会发生死锁。
  + `reboot`：在重启或应用程序启动时执行检查。届时所有过期的锁都会被释放。这是默认值。
  + `timeout`：在重启或应用程序启动时执行检查，或者在尝试锁定数据集超时时执行检查。过期的锁将立即释放。

回写机制：这些属性以 `write-behind` 键为前缀：
+ `enabled`：`true`（默认值和建议值）或 `false`，用于启用或禁用回写机制。禁用该机制会极大地影响写入性能，因此不建议这样做。
+ `maxDelay`：要触发的线程的最大持续时间。默认值为 `"1s"`（1 秒）。除非特殊情况需要调整该值，否则保持默认值通常是个不错的选择。无论如何，该值都应保持在较低水平（低于 3 秒）。该延迟字符串的格式为：`<integer value><optional whitespace><time unit>`，其中 `<time unit>` 将从以下值中选择：
  + `"ns"`：纳秒
  + `"µs"`：微秒
  + `"ms"`：毫秒
  + `"s"`：秒
+ `threads`：专用回写线程的数量。默认为 `5`。您需要根据运行Blusam引擎的主机的计算能力调整此值。使用更高的值并不意味着就能获得更高的性能，因为限制因素将变成存储 RDBMS 处理大量并发批处理查询的能力。建议值通常在 4-8 之间。
+ `batchSize`：一个正整数，表示批中将分配给线程进行批量处理的最大记录数。该值必须在 1 到 32767 之间。默认值为 `10000`。使用 `1` 作为值有违该机制的目的（即避免使用单个更新查询）；适合使用的最小值为 `1000` 左右。

嵌入式 EhCache 微调：属性以 `ehcache` key 为前缀：
+ `resource-pool`: 
  + `size`：为嵌入式缓存分配的内存大小，用字符串表示。默认为 `"1024MB"`（1 GB）。将根据托管Blusam引擎的计算机的可用内存和应用程序使用的数据集的大小进行调整。该大小字符串的格式为：`<integer value><optional whitespace><memory unit>`，其中 `<memory-unit>` 将从以下值中选择：
    + `B`：字节
    + `KB`：千字节
    + `MB`：兆字节
    +  `GB`：千兆字节
    + `TB`：兆兆字节
  + `heap`：`true` 或 `false`，用于指示缓存是否会占用 JVM 堆内存。默认为 `true`（获得最快缓存性能的选项，但缓存存储会占用 JVM 堆内 RAM 内存）。将此属性设置为 `false` 将切换到堆外内存，由于需要与 JVM 堆进行交换，会使速度变慢。
+ `timeToLiveMillis`：缓存条目在被视为过期并被删除之前在缓存中停留的持续时间（以毫秒为单位）。如果未指定此属性，则默认情况下，缓存条目不会自动过期。

##### 大型数据集的可选属性：
<a name="ba-shared-blusam-optional-properties-large-data-sets"></a>

分页索引的本地化内存缓存：
+ `indexesPrefetchWindowSize`：此属性适用于使用启用 Redis 缓存的操作的 Blusam 大型数据集。它指定了可用于存储分页索引的最大内存缓存大小（以 MB 为单位）。默认值为 0。该值可以根据可用的系统内存和正在处理的数据集的大小进行调整。

示例配置片段：

```
dataSource:
  bluesamDs:
    driver-class-name: org.postgresql.Driver
    ...
    ...
bluesam:
  locks:
    lockTimeOut: 700
  cache: ehcache
  persistence: pgsql
  ehcache:
    resource-pool:
      size: 8GB
  write-behind:
    enabled: true
    threads: 8
    batchsize: 5000
    indexesPrefetchWindowSize: 25  
  pgsql:
    dataSource : bluesamDs
```

##### 多架构配置属性
<a name="ba-shared-blusam-configuration-multi-schema"></a>
+ `multiSchema`: false（默认值）或 true，禁用或启用多架构模式 Blusam-从 4.4.0 版本开始可用。
+ `pgsql`: 
  + `schemas`：应用程序将在多架构模式下使用的架构名称列表。Blusam
  + `fallbackSchema`：用于多架构模式的备用架构名称。如果在当前架构上下文中找不到数据集，则该架构将用于对该数据集进行Blusam相关操作。

示例配置片段（启用了多架构模式）：Blusam

```
dataSource:
  bluesamDs:
    driver-class-name: org.postgresql.Driver
    ...
    ...
bluesam:
  locks:
    lockTimeOut: 700
  cache: ehcache
  persistence: pgsql
  ehcache:
    resource-pool:
      size: 8GB
  write-behind:
    enabled: true
    threads: 8
    batchsize: 5000 
  multiSchema: true 
  pgsql:
    dataSource : bluesamDs
    schemas: 
      - "schema1"
      - "schema2" 
      - "schema3"
    fallbackSchema: schema3
```

**注意**  
Blusam如果元数据架构不存在且用户有足够的权限，则会在Blusam数据库中创建这些架构，包括`application-main.yml`文件中列出的多架构模式。

## BlusamDD 文件配置
<a name="ba-shared-blusam-dd-file-configuration"></a>

这些选项可用于 groovy 中的Blusam文件配置（JCL 中的数据定义）：
+ `largeKSDS()`: 表示大型 KSDS 性质。使用时，如果指定的文件是缺失文件并且应该创建该文件（取决于打开模式和可选文件选项），则将创建一个大型 KSDS 文件及其索引表。

  ```
  .bluesam("TESTFILE").dataset("TESTFILE").largeKSDS().build()
  ```
+ `indexPageSize(Integer param)`：指定要创建的索引表的页面大小（以 mb 为单位）。适用于带`largeKSDS()`选项的文件。的值`param`应严格为正数。对于无效值，将使用默认`param`值 15。

  ```
  .bluesam("TESTFILE").dataset("TESTFILE").largeKSDS().indexPageSize(15).build()
  ```

 可以在文件中设置默认文件配置，该`ds-config.yml`文件位于`entities/src/main/resources/ds-config.yml`（或配置文件的其他位置）。当没有向运行单元提供特定的文件配置时，这些设置将用作备用配置。中支持所有 Bluesam 文件配置选项。`ds-config.yml`

```
TESTFILE:
 provider: Bluesam
 dataset: TESTFILE
 largeKSDS: true
 indexPageSize: 15
```

## Blusam管理控制台
<a name="ba-shared-blusam-administration-console"></a>

Blusam管理控制台 (BAC) 是一个 Web 应用程序，用于管理存储。Blusam有关 BAC 的信息，请参阅 [AWS 为大型机Blusam管理控制台进行转换](ba-shared-bac-userguide.md)。

## 附录
<a name="ba-shared-blusam-appendix"></a>



### 常规数据集元数据属性
<a name="ba-shared-blusam-metadata"></a>

常规数据集元数据序列化属性列表：
+ 数据集名称
+ 类型（KSDS、LargeKSDS、ESDS、LargeESDS 或 RRDS）
+ 缓存预热标志（是否在服务器启动时将数据集预加载到缓存中）
+ 压缩使用标志（以压缩格式还是原始格式存储记录）
+ 创建日期
+ 上次修改日期
+ 固定长度记录标志（数据集记录是否都具有相同的长度）
+ 记录长度：只对固定记录长度有意义
+ 页面大小（用于自定义在需要时用于预加载缓存的分页 sql 查询）
+ 大小（数据集的大小：记录的累积长度）
+ 最后偏移量 [添加到数据集的最新记录的偏移量（即 RBA）]
+ 下一个偏移量（向数据集中添加新记录的下一个可用偏移量）
+ （如果有意义）数据集使用的键的定义；每个键由其类型（主键或备用键集合的一部分）和三个属性定义：
  + 偏移量：键值起始字节在记录中的位置；
  + 长度：键值的长度（以字节为单位）。因此，键值是字节数组，该数组是从 `key offset` 位置开始，在 `key offset + length - 1` 位置结束的记录的子集；
  + 支持重复项标志：指示键是否接受重复项（设置为 true 表示支持重复项）。

### 估算给定数据集的内存占用
<a name="ba-shared-blusam-memory"></a>

对于中小型数据集，元数据（各种键的大小和索引）将完全加载到内存中。为托管用于运行现代化应用程序的服务器的计算机分配适当的资源，需要计算出Blusam数据集引起的内存消耗，尤其是元数据消耗。本节为有关的操作人员提供了切实可行的答案。

给定的公式仅适用于中Blusam小型数据集，不使用 “大” 存储策略。

#### Blusam数据集元数据
<a name="ba-shared-blusam-metadata-parts"></a>

对于Blusam数据集，元数据分为两部分：
+ 核心元数据：保存有关数据集的全局信息。与内部元数据相比，其内存占用量可以忽略不计。
+ 内部元数据：保存有关记录大小和键索引的信息；当数据集不为空时，这就是加载到托管现代化应用程序的应用程序服务器时占用内存的内容。以下各节详细说明了内存占用量如何随着记录数量的增加而增长。

#### 计算内部元数据的空间占用
<a name="ba-shared-blusam-footprint-calculation"></a>



##### 记录大小映射
<a name="ba-shared-blusam-footprint-sizesmap"></a>

首先，内部元数据存储了一个映射来保存每个记录的大小（为一个整数），给定其 RBA（相对字节地址，作为一个长数字存储）。

该数据结构的内存占用量为 `80 * number of records`（以字节为单位）

这适用于所有数据集类型。

##### 索引
<a name="ba-shared-blusam-footprint-indexes"></a>

关于 KSDS 的主键或 ESDS 和 KSDS 上的备用键的索引，空间占用量的计算取决于两个因素：
+ 数据集中的记录数；
+ 键的大小（以字节为单位）。

下图显示了基于键大小（x 轴）的每个记录的键索引大小（y 轴）。

![折线图显示随着密钥大小从 0 增加到 80，每条记录的索引大小从 83 增加到 157。](http://docs.aws.amazon.com/zh_cn/m2/latest/userguide/images/indexes_size_per_record.png)


用于估算数据集给定键索引的空间占用的相应公式为：

```
index footprint = number of records * ( 83 + 8 (key length / 8))
```

其中“/”表示整数除。

示例：
+ 数据集 1：
  + 记录数 = 459 996
  + 键长度 = 15，因此，(键长度 / 8) = 1
  + 索引占用空间 = 459 996 \* (83 \+ (8\*1)) = 41 859 636 字节（约等于 39 MB）
+ 数据集 2：
  + 记录数 = 13 095 783
  + 键长度 = 18，因此，(键长度 / 8) = 2
  + 索引占用空间 = 13 095 783 \* (83 \+ (8\*2)) = 1 296 482 517 字节（约等于 1.2 GB）

给定数据集的总占用空间是所有键索引的总占用空间与记录大小映射的占用空间之和。

例如，以只有一个键的数据集 2 为例，总占用空间为：
+ 记录大小映射：13 095 783 \* 80 = 1 047 662 640 字节
+ 键索引：1 296 482 517 字节（见上文）
+ 总占用空间 = 2 344 145 157 字节（约等于 2.18 GB）