Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

feat: add data indexing API #1255

Open
wants to merge 27 commits into
base: master
Choose a base branch
from
Open
Show file tree
Hide file tree
Changes from 6 commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
3 changes: 3 additions & 0 deletions lib/browser/client.js
Original file line number Diff line number Diff line change
Expand Up @@ -105,6 +105,9 @@ merge(proto, require('../common/bucket/getBucketWebsite'));
merge(proto, require('../common/bucket/putBucketWebsite'));
merge(proto, require('../common/bucket/deleteBucketWebsite'));

// bucket data index
merge(proto, require('../common/bucket/dataIndex'));

// lifecycle
merge(proto, require('../common/bucket/getBucketLifecycle'));
merge(proto, require('../common/bucket/putBucketLifecycle'));
Expand Down
35 changes: 35 additions & 0 deletions lib/common/bucket/dataIndex.d.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,35 @@
export declare function openMetaQuery(this: any, bucketName: string, options?: {}): Promise<{
res: any;
status: any;
}>;
export declare function getMetaQueryStatus(this: any, bucketName: string, options?: {}): Promise<{
res: any;
status: any;
}>;
interface ISubQuerie {
field?: string;
value?: string;
operation: string;
subQueries?: ISubQuerie[];
}
interface IAggregation {
field: string;
operation: string;
}
interface IMetaQuery {
nextToken?: string;
maxResults?: number;
query: ISubQuerie;
sort?: string;
order?: 'asc' | 'desc';
aggregations?: IAggregation[];
}
export declare function doMetaQuery(this: any, bucketName: string, queryParam: IMetaQuery, options?: {}): Promise<{
res: any;
status: any;
}>;
export declare function closeMetaQuery(this: any, bucketName: string, options?: {}): Promise<{
res: any;
status: any;
}>;
export {};
64 changes: 64 additions & 0 deletions lib/common/bucket/dataIndex.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,64 @@
"use strict";
Object.defineProperty(exports, "__esModule", { value: true });
exports.closeMetaQuery = exports.doMetaQuery = exports.getMetaQueryStatus = exports.openMetaQuery = void 0;
const checkBucketName_1 = require("../utils/checkBucketName");
const obj2xml_1 = require("../utils/obj2xml");
async function openMetaQuery(bucketName, options = {}) {
checkBucketName_1.checkBucketName(bucketName);
const params = this._bucketRequestParams('POST', bucketName, { metaQuery: '', comp: 'add' }, options);
const result = await this.request(params);
return {
res: result.res,
status: result.status
};
}
exports.openMetaQuery = openMetaQuery;
async function getMetaQueryStatus(bucketName, options = {}) {
checkBucketName_1.checkBucketName(bucketName);
const params = this._bucketRequestParams('GET', bucketName, 'metaQuery', options);
const result = await this.request(params);
return {
res: result.res,
status: result.status
};
}
exports.getMetaQueryStatus = getMetaQueryStatus;
async function doMetaQuery(bucketName, queryParam, options = {}) {
checkBucketName_1.checkBucketName(bucketName);
const params = this._bucketRequestParams('POST', bucketName, { metaQuery: '', comp: 'query' }, options);
const { aggregations } = queryParam;
let Aggregations;
if (aggregations && aggregations.length > 0) {
Aggregations = {
Aggregation: aggregations.map(item => ({ Field: item.field, Operation: item.operation }))
};
}
const paramXMLObj = {
MetaQuery: {
NextToken: queryParam.nextToken,
MaxResults: queryParam.maxResults,
Query: JSON.stringify(queryParam.query),
Sort: queryParam.sort,
Order: queryParam.order,
Aggregations
}
};
params.mime = 'xml';
params.content = obj2xml_1.obj2xml(paramXMLObj);
const result = await this.request(params);
return {
res: result.res,
status: result.status
};
}
exports.doMetaQuery = doMetaQuery;
async function closeMetaQuery(bucketName, options = {}) {
checkBucketName_1.checkBucketName(bucketName);
const params = this._bucketRequestParams('POST', bucketName, { metaQuery: '', comp: 'delete' }, options);
const result = await this.request(params);
return {
res: result.res,
status: result.status
};
}
exports.closeMetaQuery = closeMetaQuery;
91 changes: 91 additions & 0 deletions lib/common/bucket/dataIndex.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,91 @@
// https://help.aliyun.com/zh/oss/developer-reference/data-indexing
shungang marked this conversation as resolved.
Show resolved Hide resolved
import { checkBucketName } from '../utils/checkBucketName';
import { obj2xml } from '../utils/obj2xml';

export async function openMetaQuery(this: any, bucketName: string, options = {}) {
checkBucketName(bucketName);
const params = this._bucketRequestParams('POST', bucketName, { metaQuery: '', comp: 'add' }, options);
shungang marked this conversation as resolved.
Show resolved Hide resolved

const result = await this.request(params);
return {
res: result.res,
status: result.status
};
}

export async function getMetaQueryStatus(this: any, bucketName: string, options = {}) {
checkBucketName(bucketName);
const params = this._bucketRequestParams('GET', bucketName, 'metaQuery', options);

const result = await this.request(params);
return {
res: result.res,
status: result.status
};
}

interface ISubQuerie {
shungang marked this conversation as resolved.
Show resolved Hide resolved
// https://help.aliyun.com/zh/oss/developer-reference/appendix-supported-fields-and-operators
field?: string;
value?: string;
// 操作符。取值范围为eq(等于)、gt(大于)、gte(大于等于)、lt(小于)、 lte(小于等于)、match(模糊查询)、prefix(前缀查询)、and(逻辑与)、or(逻辑或)和not(逻辑非)。
operation: string;
subQueries?: ISubQuerie[];
}

interface IAggregation {
field: string;
operation: string;
}

interface IMetaQuery {
nextToken?: string;
maxResults?: number;
query: ISubQuerie;
sort?: string;
order?: 'asc' | 'desc';
aggregations?: IAggregation[];
}

export async function doMetaQuery(this: any, bucketName: string, queryParam: IMetaQuery, options = {}) {
checkBucketName(bucketName);
const params = this._bucketRequestParams('POST', bucketName, { metaQuery: '', comp: 'query' }, options);

const { aggregations } = queryParam;
let Aggregations;
shungang marked this conversation as resolved.
Show resolved Hide resolved
if (aggregations && aggregations.length > 0) {
Aggregations = {
Aggregation: aggregations.map(item => ({ Field: item.field, Operation: item.operation }))
};
}

const paramXMLObj = {
MetaQuery: {
NextToken: queryParam.nextToken,
MaxResults: queryParam.maxResults,
Query: JSON.stringify(queryParam.query),
Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

这里直接转成JSON字符串了,里面的key不需要处理成大写吗

Sort: queryParam.sort,
Order: queryParam.order,
Aggregations
}
};
params.mime = 'xml';
params.content = obj2xml(paramXMLObj);

const result = await this.request(params);
return {
res: result.res,
status: result.status
};
}

export async function closeMetaQuery(this: any, bucketName: string, options = {}) {
checkBucketName(bucketName);
const params = this._bucketRequestParams('POST', bucketName, { metaQuery: '', comp: 'delete' }, options);

const result = await this.request(params);
return {
res: result.res,
status: result.status
};
}
1 change: 1 addition & 0 deletions lib/common/bucket/index.js
Original file line number Diff line number Diff line change
Expand Up @@ -32,3 +32,4 @@ merge(proto, require('./extendBucketWorm'));
merge(proto, require('./getBucketWorm'));
merge(proto, require('./initiateBucketWorm'));
merge(proto, require('./getBucketStat'));
merge(proto, require('./dataIndex'));
23 changes: 23 additions & 0 deletions test/browser/browser.test.js
Original file line number Diff line number Diff line change
Expand Up @@ -38,6 +38,7 @@ const cleanBucket = async store => {
const uploads = result.uploads || [];
await Promise.all(uploads.map(_ => store.abortMultipartUpload(_.name, _.uploadId)));
};

describe('browser', () => {
/* eslint require-yield: [0] */
before(() => {
Expand Down Expand Up @@ -2509,4 +2510,26 @@ describe('browser', () => {
}
});
});

// oss server 不支持跨域 大概要到9月30号才上生产支持 跨域,后端是:云仁
Copy link
Collaborator

@YunZZY YunZZY Oct 17, 2023

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

现在应该可以了,这里的case加一下,要保证所有的参数都有设置一下,保证覆盖率

describe.skip('bucket data index', () => {
let store;
before(async () => {
store = oss({ ...ossConfig, refreshSTSTokenInterval: 1000 });
});

it('open meta query of bucket', async () => {
try {
// await store.listV2({ 'max-keys': 1 });
// const result = await store.getMetaQueryStatus(stsConfig.bucket); // oss server does not support cross domain
const result = await store.openMetaQuery(stsConfig.bucket);
console.log('rr', result);
assert.strictEqual(result.status, 200);
assert.deepEqual(result.res.statusMessage, 'OK');
} catch (error) {
Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

这里的catch没有必要,接口报错本身case就是要失败的,错误码不限于这两个
另:open确实需要些时间,可以加点时间等一等

console.log('bb', JSON.stringify(error), error);
assert.fail(error);
}
});
});
});
59 changes: 59 additions & 0 deletions test/node/bucket.test.js
Original file line number Diff line number Diff line change
Expand Up @@ -1480,4 +1480,63 @@ describe('test/bucket.test.js', () => {
});
});
});

describe('openMetaQuery() openMetaQuery() doMetaQuery() closeMetaQuery()', () => {
Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

  1. 这里的描述改一下,和上面的一样
  2. 这里的所有case,都和上面的一样,改一下

it('open meta query of bucket', async () => {
try {
const result = await store.openMetaQuery(bucket);
assert.strictEqual(result.status, 200);
assert.deepEqual(result.res.statusMessage, 'OK');
} catch (error) {
assert.fail(error);
}
});

it('getMetaQueryStatus()', async () => {
try {
const result = await store.getMetaQueryStatus(bucket);
assert.strictEqual(result.status, 200);
assert.deepEqual(result.res.statusMessage, 'OK');
} catch (error) {
assert.fail(error);
}
});

it('doMetaQuery()', async () => {
try {
const queryParam = {
query: { operation: 'and', subQueries: [{ Field: 'Size', Value: '1048576', Operation: 'lt' }] }
Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

参数设置全一些,都覆盖一下吧,参考一下文档示例

};
const result = await store.doMetaQuery(bucket, queryParam);
assert.strictEqual(result.status, 200);
assert.deepEqual(result.res.statusMessage, 'OK');
} catch (error) {
assert.fail(error);
}
});

it('doMetaQuery() Aggregations', async () => {
try {
const queryParam = {
query: { operation: 'and', subQueries: [{ Field: 'Size', Value: '1048576', Operation: 'lt' }] },
Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

参数设置全一些,subQueries类型这里对不上,改一下

aggregations: [{ field: 'Size', operation: 'sum' }]
};
const result = await store.doMetaQuery(bucket, queryParam);
assert.strictEqual(result.status, 200);
assert.deepEqual(result.res.statusMessage, 'OK');
} catch (error) {
assert.fail(error);
}
});

it('closeMetaQuery()', async () => {
shungang marked this conversation as resolved.
Show resolved Hide resolved
try {
const result = await store.closeMetaQuery(bucket);
assert.strictEqual(result.status, 200);
assert.deepEqual(result.res.statusMessage, 'OK');
} catch (error) {
assert.fail(error);
}
});
});
});