传统的视频检索依赖人工打标或事后翻看录像,难以从海量视频中快速定位「有人摔倒」「有人撒网」「违规广告」这类特定事件。自定义事件侦测让您用一句话描述业务关心的事件,视频入库时由 AI 自动识别并打上事件标签、写入文件元数据;之后通过元数据查询接口即可直接检索命中事件的视频,无需自建视频理解链路。
本功能基于新版 MetaQuery,当前处于邀测阶段,仅支持华东1(杭州)、新加坡地域。使用前请确保目标 Bucket 位于上述地域,并联系技术支持申请开通新版 MetaQuery 邀测能力。
应用场景
安防监控:从海量监控视频中自动识别「有人摔倒」「有人翻越围栏」等安全事件,便于事后检索与告警联动。
内容审核:对 UGC 视频自动标记「违规广告」「违规手势」等业务自定义违规事件,辅助人工复核。
行业巡检:对生产、渔业、交通等场景的视频自动标记业务关注的特定行为,沉淀为可检索的结构化标签。
工作原理
定义事件标签:在目标 Dataset 的
DatasetConfig中开启用户自定义标签,为每个事件配置名称(Name)和触发条件描述(Description)。入库自动识别:视频上传并路由到该 Dataset 后,OSS 异步对视频做内容理解,按标签的描述匹配画面中发生的事件。
写入元数据:匹配到的事件标签写入该文件在 Dataset 中的元数据(
Labels)。按标签检索:通过
SimpleQuery按Labels.LabelName检索命中事件的文件;也可通过 MNS 通知获取命中的标签。
视频内容理解为异步执行,上传后需要等待一段时间事件标签才会生成;在此之前文件可能查询不到。
使用限制
调用方需具备
oss:MetaQuery、oss:PutObject等权限。如需接收文件索引完成通知,请提前创建 MNS 队列,并确保
OpenMetaQuery使用的 RAM 角色拥有向该队列发送消息的权限。如需将不同对象路由到不同 Dataset,需要在开启 MetaQuery 时配置
RouteRule。
1. 开启 MetaQuery
以 semantic 模式为 Bucket 开启元数据管理功能。以下示例基于 OSS Java SDK V2(com.aliyun:alibabacloud-oss-v2)与 OSS Go SDK V2(github.com/aliyun/alibabacloud-oss-go-sdk-v2),并从环境变量 OSS_ACCESS_KEY_ID、OSS_ACCESS_KEY_SECRET 读取访问凭证。
Java SDK
import com.aliyun.sdk.service.oss2.credentials.EnvironmentVariableCredentialsProvider;
import com.aliyun.sdk.service.oss2.dataprocess.OSSDataProcessClient;
import com.aliyun.sdk.service.oss2.dataprocess.models.*;
import java.util.Arrays;
import java.util.Collections;
public class OpenMetaQuerySample {
public static void main(String[] args) throws Exception {
try (OSSDataProcessClient client = OSSDataProcessClient.newBuilder()
.region("cn-hangzhou")
.credentialsProvider(new EnvironmentVariableCredentialsProvider())
.build()) {
MetaQueryOpenBody body = MetaQueryOpenBody.newBuilder()
.routeRule(RouteRule.newBuilder()
.type("OSSTag")
.autoCreateDataset("True")
.ossTagKey("routing-dataset")
.build())
.notificationAttributes(NotificationAttributes.newBuilder()
.notifications(MetaQueryNotifications.newBuilder()
.notifications(Collections.singletonList(
MetaQueryNotification.newBuilder()
.mns("metaquery-index-notification")
.build()))
.build())
.withFields(Arrays.asList("Labels", "Insights"))
.build())
.build();
client.openMetaQuery(OpenMetaQueryRequest.newBuilder()
.bucket("examplebucket")
.mode("semantic")
.role("AliyunMetaQueryDefaultRole")
.metaQueryBody(body)
.build());
System.out.println("open meta query success");
}
}
}多 Dataset 路由(RouteRule)、索引完成 MNS 通知(NotificationAttributes)以及 Bucket 级默认 DatasetConfig,需在 OpenMetaQuery 请求体中一并配置,字段说明请参见 OpenMetaQuery;如需在通知消息中返回事件标签,请在 WithFields 中加入 Labels。
2. 创建 Dataset 并配置事件标签
调用 CreateDataset 创建 Dataset,并通过 DatasetConfig 配置自定义事件标签:将 Insights.Video.Label.UserDefined.Enable 设置为 true,并在 Labels 中配置标签清单。各字段含义如下。
字段 | 说明 |
Name | 标签名称,查询时按该名称检索。例如 |
Description | 标签的触发条件描述,作为 AI 匹配的语义提示。建议写清动作、场景和关键细节,例如 |
Java SDK
import com.aliyun.sdk.service.oss2.credentials.EnvironmentVariableCredentialsProvider;
import com.aliyun.sdk.service.oss2.dataprocess.OSSDataProcessClient;
import com.aliyun.sdk.service.oss2.dataprocess.models.*;
import java.util.Arrays;
public class CreateDatasetSample {
public static void main(String[] args) throws Exception {
try (OSSDataProcessClient client = OSSDataProcessClient.newBuilder()
.region("cn-hangzhou")
.credentialsProvider(new EnvironmentVariableCredentialsProvider())
.build()) {
DatasetConfig config = DatasetConfig.newBuilder()
.insights(InsightsConfig.newBuilder()
.video(InsightsVideoConfig.newBuilder()
.label(InsightsVideoLabelConfig.newBuilder()
.userDefined(InsightsLabelUserDefinedConfig.newBuilder()
.enable("true")
.labels(Arrays.asList(
InsightsLabelItem.newBuilder()
.name("有人摔倒")
.description("画面中有人由站立或行走变为倒在地面的动作")
.build(),
InsightsLabelItem.newBuilder()
.name("有人撒网")
.description("有人在水边或船上进行撒网捞鱼的动作")
.build()))
.build())
.build())
.build())
.build())
.build();
client.createDataset(CreateDatasetRequest.newBuilder()
.bucket("examplebucket")
.datasetName("security-events")
.datasetConfig(config)
.build());
System.out.println("create dataset success");
}
}
}兼容旧版本的基础自定义标签开关也可通过 WorkflowParameters 配置,该方式仅用于存量配置,后续新功能不再通过 WorkflowParameters 演进。新接入建议统一使用 DatasetConfig。
3. 上传视频并路由到 Dataset
上传视频时,通过 OSS Object Tag 设置 routing-dataset=security-events,将文件路由到目标 Dataset。文件索引完成后,会按照 Dataset 中配置的标签清单进行事件匹配。
Java SDK
import com.aliyun.sdk.service.oss2.OSSClient;
import com.aliyun.sdk.service.oss2.credentials.EnvironmentVariableCredentialsProvider;
import com.aliyun.sdk.service.oss2.models.PutObjectRequest;
import com.aliyun.sdk.service.oss2.transport.BinaryData;
import java.nio.file.Files;
import java.nio.file.Paths;
public class PutObjectSample {
public static void main(String[] args) throws Exception {
try (OSSClient client = OSSClient.newBuilder()
.region("cn-hangzhou")
.credentialsProvider(new EnvironmentVariableCredentialsProvider())
.build()) {
client.putObject(PutObjectRequest.newBuilder()
.bucket("examplebucket")
.key("security/event-a.mp4")
.tagging("routing-dataset=security-events")
.body(BinaryData.fromStream(Files.newInputStream(Paths.get("/local/path/event-a.mp4"))))
.build());
System.out.println("put object success");
}
}
}(可选)为单个文件附加临时标签
如果某个文件需要使用 Dataset 标签清单之外的临时标签,可以在上传时通过自定义元数据头携带 URL 编码后的标签清单。HTTP 头名称为 x-oss-meta-metaquery-user-defined-labels;使用 SDK 时,metadata 的 key 填写 metaquery-user-defined-labels。
Java SDK
import com.aliyun.sdk.service.oss2.OSSClient;
import com.aliyun.sdk.service.oss2.credentials.EnvironmentVariableCredentialsProvider;
import com.aliyun.sdk.service.oss2.models.PutObjectRequest;
import com.aliyun.sdk.service.oss2.transport.BinaryData;
import java.net.URLEncoder;
import java.nio.charset.StandardCharsets;
import java.nio.file.Files;
import java.nio.file.Paths;
import java.util.Collections;
public class PutObjectWithLabelsSample {
public static void main(String[] args) throws Exception {
String labels = URLEncoder.encode(
"[{\"Name\":\"有人摔倒\",\"Description\":\"画面中有人由站立或行走变为倒在地面的动作\"}]",
StandardCharsets.UTF_8);
try (OSSClient client = OSSClient.newBuilder()
.region("cn-hangzhou")
.credentialsProvider(new EnvironmentVariableCredentialsProvider())
.build()) {
client.putObject(PutObjectRequest.newBuilder()
.bucket("examplebucket")
.key("security/event-x.mp4")
.tagging("routing-dataset=security-events")
.metadata(Collections.singletonMap("metaquery-user-defined-labels", labels))
.body(BinaryData.fromStream(Files.newInputStream(Paths.get("/local/path/event-x.mp4"))))
.build());
System.out.println("put object success");
}
}
}4. 查询命中文件
文件索引完成后,调用 SimpleQuery 在指定 Dataset 内按 Labels.LabelName 精确查询命中文件。如果在开启 MetaQuery 时配置了 MNS 通知,您也可以通过消费 MNS 消息判断文件是否索引完成,并从通知消息中读取命中的 Labels。
Java SDK
import com.aliyun.sdk.service.oss2.credentials.EnvironmentVariableCredentialsProvider;
import com.aliyun.sdk.service.oss2.dataprocess.OSSDataProcessClient;
import com.aliyun.sdk.service.oss2.dataprocess.models.*;
import java.util.Arrays;
public class SimpleQueryLabelSample {
public static void main(String[] args) throws Exception {
try (OSSDataProcessClient client = OSSDataProcessClient.newBuilder()
.region("cn-hangzhou")
.credentialsProvider(new EnvironmentVariableCredentialsProvider())
.build()) {
SimpleQueryResult result = client.simpleQuery(SimpleQueryRequest.newBuilder()
.bucket("examplebucket")
.datasetName("security-events")
.query(SimpleQuery.newBuilder()
.field("Labels.LabelName")
.operation("eq")
.value("有人摔倒")
.build())
.withFields(Arrays.asList("Filename", "URI", "Labels"))
.maxResults(20)
.build());
for (File file : result.files()) {
System.out.println(file.filename() + " " + file.labels());
}
}
}
}响应中每个命中文件的 Labels.Label.LabelName 字段即为匹配的业务标签。例如:
<File>
<Filename>security/event-a.mp4</Filename>
<Labels>
<Label>
<LabelName>有人摔倒</LabelName>
</Label>
</Labels>
</File>相关 API
开启元数据管理功能:OpenMetaQuery
创建 Dataset 并配置事件标签:CreateDataset
按标签查询命中文件:SimpleQuery
事件标签配置的数据结构:DatasetConfig