Added iOS language detector tests
This commit is contained in:
parent
b5b0d6eee7
commit
9d9a5dc5e7
61
mediapipe/tasks/ios/test/text/language_detector/BUILD
Normal file
61
mediapipe/tasks/ios/test/text/language_detector/BUILD
Normal file
|
@ -0,0 +1,61 @@
|
||||||
|
load(
|
||||||
|
"@build_bazel_rules_apple//apple:ios.bzl",
|
||||||
|
"ios_unit_test",
|
||||||
|
)
|
||||||
|
load(
|
||||||
|
"@build_bazel_rules_swift//swift:swift.bzl",
|
||||||
|
"swift_library",
|
||||||
|
)
|
||||||
|
load(
|
||||||
|
"//mediapipe/framework/tool:ios.bzl",
|
||||||
|
"MPP_TASK_MINIMUM_OS_VERSION",
|
||||||
|
)
|
||||||
|
load(
|
||||||
|
"@org_tensorflow//tensorflow/lite:special_rules.bzl",
|
||||||
|
"tflite_ios_lab_runner",
|
||||||
|
)
|
||||||
|
|
||||||
|
package(default_visibility = ["//mediapipe/tasks:internal"])
|
||||||
|
|
||||||
|
licenses(["notice"])
|
||||||
|
|
||||||
|
# Default tags for filtering iOS targets. Targets are restricted to Apple platforms.
|
||||||
|
TFL_DEFAULT_TAGS = [
|
||||||
|
"apple",
|
||||||
|
]
|
||||||
|
|
||||||
|
# Following sanitizer tests are not supported by iOS test targets.
|
||||||
|
TFL_DISABLED_SANITIZER_TAGS = [
|
||||||
|
"noasan",
|
||||||
|
"nomsan",
|
||||||
|
"notsan",
|
||||||
|
]
|
||||||
|
|
||||||
|
objc_library(
|
||||||
|
name = "MPPLanguageDetectorObjcTestLibrary",
|
||||||
|
testonly = 1,
|
||||||
|
srcs = ["MPPLanguageDetectorTests.mm"],
|
||||||
|
copts = [
|
||||||
|
"-ObjC++",
|
||||||
|
"-std=c++17",
|
||||||
|
"-x objective-c++",
|
||||||
|
],
|
||||||
|
data = [
|
||||||
|
"//mediapipe/tasks/testdata/text:language_detector",
|
||||||
|
],
|
||||||
|
deps = [
|
||||||
|
"//mediapipe/tasks/ios/common:MPPCommon",
|
||||||
|
"//mediapipe/tasks/ios/text/language_detector:MPPLanguageDetector",
|
||||||
|
"//mediapipe/tasks/ios/test/utils:MPPFileInfo",
|
||||||
|
],
|
||||||
|
)
|
||||||
|
|
||||||
|
ios_unit_test(
|
||||||
|
name = "MPPLanguageDetectorObjcTest",
|
||||||
|
minimum_os_version = MPP_TASK_MINIMUM_OS_VERSION,
|
||||||
|
runner = tflite_ios_lab_runner("IOS_LATEST"),
|
||||||
|
tags = TFL_DEFAULT_TAGS + TFL_DISABLED_SANITIZER_TAGS,
|
||||||
|
deps = [
|
||||||
|
":MPPLanguageDetectorObjcTestLibrary",
|
||||||
|
],
|
||||||
|
)
|
|
@ -0,0 +1,162 @@
|
||||||
|
// Copyright 2023 The MediaPipe Authors.
|
||||||
|
//
|
||||||
|
// Licensed under the Apache License, Version 2.0 (the "License");
|
||||||
|
// you may not use this file except in compliance with the License.
|
||||||
|
// You may obtain a copy of the License at
|
||||||
|
//
|
||||||
|
// http://www.apache.org/licenses/LICENSE-2.0
|
||||||
|
//
|
||||||
|
// Unless required by applicable law or agreed to in writing, software
|
||||||
|
// distributed under the License is distributed on an "AS IS" BASIS,
|
||||||
|
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||||
|
// See the License for the specific language governing permissions and
|
||||||
|
// limitations under the License.
|
||||||
|
|
||||||
|
#import <XCTest/XCTest.h>
|
||||||
|
|
||||||
|
#import "mediapipe/tasks/ios/common/sources/MPPCommon.h"
|
||||||
|
#import "mediapipe/tasks/ios/test/utils/sources/MPPFileInfo.h"
|
||||||
|
#import "mediapipe/tasks/ios/text/language_detector/sources/MPPLanguageDetector.h"
|
||||||
|
|
||||||
|
static MPPFileInfo *const kLanguageDetectorModelFileInfo =
|
||||||
|
[[MPPFileInfo alloc] initWithName:@"language_detector" type:@"tflite"];
|
||||||
|
|
||||||
|
static NSString *const kExpectedErrorDomain = @"com.google.mediapipe.tasks";
|
||||||
|
|
||||||
|
#define AssertEqualErrors(error, expectedError) \
|
||||||
|
XCTAssertNotNil(error); \
|
||||||
|
XCTAssertEqualObjects(error.domain, expectedError.domain); \
|
||||||
|
XCTAssertEqual(error.code, expectedError.code); \
|
||||||
|
XCTAssertEqualObjects(error.localizedDescription, expectedError.localizedDescription)
|
||||||
|
|
||||||
|
@interface MPPLanguageDetectorTests : XCTestCase
|
||||||
|
@end
|
||||||
|
|
||||||
|
@implementation MPPLanguageDetectorTests
|
||||||
|
|
||||||
|
- (void)testCreateLanguageDetectorFailsWithMissingModelPath {
|
||||||
|
MPPFileInfo *fileInfo = [[MPPFileInfo alloc] initWithName:@"" type:@""];
|
||||||
|
|
||||||
|
NSError *error = nil;
|
||||||
|
MPPLanguageDetector *languageDetector =
|
||||||
|
[[MPPLanguageDetector alloc] initWithModelPath:fileInfo.path error:&error];
|
||||||
|
XCTAssertNil(languageDetector);
|
||||||
|
|
||||||
|
NSError *expectedError = [NSError
|
||||||
|
errorWithDomain:kExpectedErrorDomain
|
||||||
|
code:MPPTasksErrorCodeInvalidArgumentError
|
||||||
|
userInfo:@{
|
||||||
|
NSLocalizedDescriptionKey :
|
||||||
|
@"INVALID_ARGUMENT: ExternalFile must specify at least one of 'file_content', "
|
||||||
|
@"'file_name', 'file_pointer_meta' or 'file_descriptor_meta'."
|
||||||
|
}];
|
||||||
|
AssertEqualErrors(error, expectedError);
|
||||||
|
}
|
||||||
|
|
||||||
|
- (void)testCreateLanguageDetectorFailsWithBothAllowlistAndDenylist {
|
||||||
|
MPPLanguageDetectorOptions *options =
|
||||||
|
[self languageDetectorOptionsWithModelFileInfo:kLanguageDetectorModelFileInfo];
|
||||||
|
options.categoryAllowlist = @[ @"en" ];
|
||||||
|
options.categoryDenylist = @[ @"en" ];
|
||||||
|
|
||||||
|
[self assertCreateLanguageDetectorWithOptions:options
|
||||||
|
failsWithExpectedError:
|
||||||
|
[NSError
|
||||||
|
errorWithDomain:kExpectedErrorDomain
|
||||||
|
code:MPPTasksErrorCodeInvalidArgumentError
|
||||||
|
userInfo:@{
|
||||||
|
NSLocalizedDescriptionKey :
|
||||||
|
@"INVALID_ARGUMENT: `category_allowlist` and "
|
||||||
|
@"`category_denylist` are mutually exclusive options."
|
||||||
|
}]];
|
||||||
|
}
|
||||||
|
|
||||||
|
- (void)testCreateLanguageDetectorFailsWithInvalidMaxResults {
|
||||||
|
MPPLanguageDetectorOptions *options =
|
||||||
|
[self languageDetectorOptionsWithModelFileInfo:kLanguageDetectorModelFileInfo];
|
||||||
|
options.maxResults = 0;
|
||||||
|
|
||||||
|
[self
|
||||||
|
assertCreateLanguageDetectorWithOptions:options
|
||||||
|
failsWithExpectedError:
|
||||||
|
[NSError errorWithDomain:kExpectedErrorDomain
|
||||||
|
code:MPPTasksErrorCodeInvalidArgumentError
|
||||||
|
userInfo:@{
|
||||||
|
NSLocalizedDescriptionKey :
|
||||||
|
@"INVALID_ARGUMENT: Invalid `max_results` option: "
|
||||||
|
@"value must be != 0."
|
||||||
|
}]];
|
||||||
|
}
|
||||||
|
|
||||||
|
- (void)testClassifyWithL2CModelSucceeds {
|
||||||
|
MPPLanguageDetectorOptions *options =
|
||||||
|
[self languageDetectorOptionsWithModelFileInfo:kLanguageDetectorModelFileInfo];
|
||||||
|
|
||||||
|
MPPLanguageDetector *languageDetector = [self createLanguageDetectorWithOptionsSucceeds:options];
|
||||||
|
NSString *enText = @"To be, or not to be, that is the question";
|
||||||
|
NSArray<MPPLanguagePrediction *> *expectedEnLanguagePredictions =
|
||||||
|
@[ [[MPPLanguagePrediction alloc] initWithLanguageCode:@"en" probability:0.9998559f] ];
|
||||||
|
|
||||||
|
[self assertResultsOfDetectLanguageOfText:enText
|
||||||
|
usingLanguageDetector:languageDetector
|
||||||
|
approximatelyEqualsExpectedLanguagePredictions:expectedEnLanguagePredictions];
|
||||||
|
|
||||||
|
NSString *frText = @"Il y a beaucoup de bouches qui parlent et fort peu de têtes qui pensent.";
|
||||||
|
NSArray<MPPLanguagePrediction *> *expectedFrLanguagePredictions =
|
||||||
|
@[ [[MPPLanguagePrediction alloc] initWithLanguageCode:@"fr" probability:0.9997813f] ];
|
||||||
|
|
||||||
|
[self assertResultsOfDetectLanguageOfText:frText
|
||||||
|
usingLanguageDetector:languageDetector
|
||||||
|
approximatelyEqualsExpectedLanguagePredictions:expectedFrLanguagePredictions];
|
||||||
|
|
||||||
|
NSString *ruText = @"это какой-то английский язык";
|
||||||
|
NSArray<MPPLanguagePrediction *> *expectedRuLanguagePredictions =
|
||||||
|
@[ [[MPPLanguagePrediction alloc] initWithLanguageCode:@"ru" probability:0.9933616f] ];
|
||||||
|
|
||||||
|
[self assertResultsOfDetectLanguageOfText:ruText
|
||||||
|
usingLanguageDetector:languageDetector
|
||||||
|
approximatelyEqualsExpectedLanguagePredictions:expectedRuLanguagePredictions];
|
||||||
|
}
|
||||||
|
|
||||||
|
#pragma mark Assert Segmenter Results
|
||||||
|
- (void)assertResultsOfDetectLanguageOfText:(NSString *)text
|
||||||
|
usingLanguageDetector:(MPPLanguageDetector *)languageDetector
|
||||||
|
approximatelyEqualsExpectedLanguagePredictions:
|
||||||
|
(NSArray<MPPLanguagePrediction *> *)expectedLanguagePredictions {
|
||||||
|
MPPLanguageDetectorResult *result = [languageDetector detectText:text error:nil];
|
||||||
|
XCTAssertNotNil(result);
|
||||||
|
XCTAssertEqualWithAccuracy(result.languagePredictions[0].probability,
|
||||||
|
expectedLanguagePredictions[0].probability, 1e-3);
|
||||||
|
XCTAssertEqualObjects(result.languagePredictions[0].languageCode,
|
||||||
|
expectedLanguagePredictions[0].languageCode);
|
||||||
|
}
|
||||||
|
|
||||||
|
#pragma mark Language Detector Initializers
|
||||||
|
|
||||||
|
- (MPPLanguageDetectorOptions *)languageDetectorOptionsWithModelFileInfo:(MPPFileInfo *)fileInfo {
|
||||||
|
MPPLanguageDetectorOptions *options = [[MPPLanguageDetectorOptions alloc] init];
|
||||||
|
options.baseOptions.modelAssetPath = fileInfo.path;
|
||||||
|
return options;
|
||||||
|
}
|
||||||
|
|
||||||
|
- (MPPLanguageDetector *)createLanguageDetectorWithOptionsSucceeds:
|
||||||
|
(MPPLanguageDetectorOptions *)options {
|
||||||
|
NSError *error;
|
||||||
|
MPPLanguageDetector *languageDetector = [[MPPLanguageDetector alloc] initWithOptions:options
|
||||||
|
error:&error];
|
||||||
|
XCTAssertNotNil(languageDetector);
|
||||||
|
XCTAssertNil(error);
|
||||||
|
|
||||||
|
return languageDetector;
|
||||||
|
}
|
||||||
|
|
||||||
|
- (void)assertCreateLanguageDetectorWithOptions:(MPPLanguageDetectorOptions *)options
|
||||||
|
failsWithExpectedError:(NSError *)expectedError {
|
||||||
|
NSError *error = nil;
|
||||||
|
MPPLanguageDetector *languageDetector = [[MPPLanguageDetector alloc] initWithOptions:options
|
||||||
|
error:&error];
|
||||||
|
XCTAssertNil(languageDetector);
|
||||||
|
AssertEqualErrors(error, expectedError);
|
||||||
|
}
|
||||||
|
|
||||||
|
@end
|
Loading…
Reference in New Issue
Block a user