Identification API

Request this API you should use “multipart/form-data” Content-Type. You can use this API to identify all of the audio formats or fingerprint extracted with our SDK/Tools. We suggest you use data type “fingerprint”, which will reduce the internet bandwidth and accelerate recognition speeds. Also, we suggest you do not use a large file to request this API, this can cause delays, its advised to reduce the file size before upload, files that are less than 15 seconds are generally better.

post
Identifying an audio file or a fingerprint file

https://identify-eu-west-1.acrcloud.com/v1/identify
Request
Response
Request
Form Data Parameters
sample
required
object
The audio file or the fingerprint file
access_key
required
string
The project access_key
sample_bytes
required
number
The file size
timestamp
required
string
Timestamp (the time since the Epoch)
signature
required
string
Requests to ACRCloud server must be signed. That is, they must include information that ACRCloud can use to authenticate the requestor. string_to_sign = http_method+"\n" +http_uri+"\n" +access_key+"\n" +data_type+"\n" +signature_version+"\n" +timestamp signature = base64.b64encode(hmac.new(access_secret, string_to_sign, digestmod=hashlib.sha1).digest())
data_type
required
string
audio or fingerprint
signature_version
required
number
1
Response
200: OK
{
"metadata":{
"timestamp_utc":"2020-01-19 02:58:28",
"music":[
{
"db_begin_time_offset_ms":0,
"db_end_time_offset_ms":9280,
"sample_begin_time_offset_ms":0,
"sample_end_time_offset_ms":9280,
"play_offset_ms":9040,
"artists":[
{
"name":"Adele",
"langs":[{"code":"zh-Hans", "name":"阿黛尔"}]
}
],
"lyrics":{
"copyrights":[
"Sony/ATV Music Publishing LLC",
"Universal Music Publishing Group"
]
},
"acrid":"6049f11da7095e8bb8266871d4a70873",
"album":{
"name":"Hello",
"langs":[{"code":"zh-Hans","name":"Hello"}]
},
"rights_claim": [
{"distributor":{"id":"PADPIDA2007050901U", "name":"Warner Music Group"},"rights_owners":[{"name":"Warner Music Group", "share_percentage":100.00}],"rights_claim_policy":"monetize", "territories":["AD","AE","AF"]},
{"distributor":{"id":"PADPIDA2007040502I", "name":"Sony Music Entertainment"}, "rights_owners":[{"name":"Sony Music Entertainment", "share_percentage":100.00}],"territories":["AB","AC"]}
],
"external_ids":{
"iswc":"T-917.819.808-8",
"isrc":"GBBKS1500214",
"upc":"886445581959"
},
"result_from":3,
"contributors":{
"composers":[
"Adele Adkins",
"Greg Kurstin"
],
"lyricists":[
"ADELE ADKINS",
"GREGORY KURSTIN"
]
},
"title":"Hello",
"langs":[{"code":"zh-Hans","name":"Hello"}]
"language":"en",
"duration_ms":295000,
"label":"XL Recording",
"external_metadata":{
"musicbrainz":[
{
"track":{
"id":"0a8e8d55-4b83-4f8a-9732-fbb5ded9f344"
}
}
],
"deezer":{
"track":{
"id":"110265034"
},
"artists":[
{
"id":"75798"
}
],
"album":{
"id":"11483764"
}
},
"spotify":{
"track":{
"id":"4aebBr4JAihzJQR0CiIZJv"
},
"artists":[
{
"id":"4dpARuHxo51G3z768sgnrY"
}
],
"album":{
"id":"7uwTHXmFa1Ebi5flqBosig"
}
},
"musicstory":{
"track":{
"id":"13106540"
},
"album":{
"id":"931271"
}
},
"youtube":{
"vid":"YQHsXMglC9A"
}
},
"score":100,
"genres":[{"name":"Pop"}],
"release_date":"2015-10-23"
"release_by_territories": [{"territories": ["DK"], "release_date": "2006-04-17"}, {"territories": ["JP"], "release_date": "2006-10-17"}, {"territories": ["SE"], "release_date": "2005-06-21"}, {"territories": ["BG", "AL", "BA", "CZ", "EE", "HR", "HU", "LT", "LV", "MK", "ME", "PL", "RO", "RS", "SI", "SK", "UA"], "release_date": "2006-03-24"}, {"territories": ["GB", "IE", "NZ"], "release_date": "2005-07-18"}, {"territories": ["FR"], "release_date": "2005-07-26"}]
}
]
},
"status":{
"msg":"Success",
"version":"1.0",
"code":0
},
"result_type":0
}
Python
PHP
Java
Javascript
ReactNative
Ruby
Python
'''
This is a demo program which implements ACRCloud Identify Protocol V1 with the third party library "requests".
We recomment you implement your own app with "requests" too.
You can install this python library by:
1) sudo easy_install requests
2) sudo pip install requests
'''
import sys
import os
import base64
import hmac
import hashlib
import time
import requests
'''
Replace "###...###" below with your project's host, access_key and access_secret.
'''
access_key = "###YOUR_ACCESS_KEY###"
access_secret = "###YOUR_ACCESS_SECRET###"
requrl = "http://###YOUR_HOST###/v1/identify"
http_method = "POST"
http_uri = "/v1/identify"
#default is "fingerprint", it's for recognizing fingerprint, if you want to identify audio, please change data_type="audio"
data_type = "audio"
signature_version = "1"
timestamp = time.time()
string_to_sign = http_method+"\n"+http_uri+"\n"+access_key+"\n"+data_type+"\n"+signature_version+"\n"+str(timestamp)
sign = base64.b64encode(hmac.new(access_secret, string_to_sign, digestmod=hashlib.sha1).digest())
# suported file formats: mp3,wav,wma,amr,ogg, ape,acc,spx,m4a,mp4,FLAC, etc
# File size: < 1M , You'de better cut large file to small file, within 15 seconds data size is better
f = open(sys.argv[1], "rb")
sample_bytes = os.path.getsize(sys.argv[1])
files=[
('sample',('test.mp3',open('/Users/olym/Downloads/test.mp3','rb'),'audio/mpeg'))
]
data = {'access_key':access_key,
'sample_bytes':sample_bytes,
'timestamp':str(timestamp),
'signature':sign,
'data_type':data_type,
"signature_version":signature_version}
r = requests.post(requrl, files=files, data=data)
r.encoding = "utf-8"
print r.text
PHP
<?php
$http_method = "POST";
$http_uri = "/v1/identify";
$data_type = "audio";
$signature_version = "1" ;
$timestamp = time() ;
// Replace "###...###" below with your project's host, access_key and access_secret.
$requrl = "http://###YOUR_HOST###/v1/identify";
$access_key = '###YOUR_ACCESS_KEY###';
$access_secret = '###YOUR_ACCESS_SECRET###';
$string_to_sign = $http_method . "\n" .
$http_uri ."\n" .
$access_key . "\n" .
$data_type . "\n" .
$signature_version . "\n" .
$timestamp;
$signature = hash_hmac("sha1", $string_to_sign, $access_secret, true);
$signature = base64_encode($signature);
// suported file formats: mp3,wav,wma,amr,ogg, ape,acc,spx,m4a,mp4,FLAC, etc
// File size: < 1M , You'de better cut large file to small file, within 15 seconds data size is better
$file = $argv[1];
$filesize = filesize($file);
$cfile = new CURLFile($file, "mp3", basename($argv[1]));
$postfields = array(
"sample" => $cfile,
"sample_bytes"=>$filesize,
"access_key"=>$access_key,
"data_type"=>$data_type,
"signature"=>$signature,
"signature_version"=>$signature_version,
"timestamp"=>$timestamp);
$ch = curl_init();
curl_setopt($ch, CURLOPT_URL, $requrl);
curl_setopt($ch, CURLOPT_POST, true);
curl_setopt($ch, CURLOPT_POSTFIELDS, $postfields);
curl_setopt($ch, CURLOPT_RETURNTRANSFER, 1);
$result = curl_exec($ch);
echo $result;
//$response = curl_exec($ch);
//if ($response == true) {
// $info = curl_getinfo($ch);
//} else {
// $errmsg = curl_error($ch);
// print $errmsg;
//}
curl_close($ch);
?>
Java
import java.io.BufferedOutputStream;
import java.io.BufferedReader;
import java.io.ByteArrayOutputStream;
import java.io.File;
import java.io.FileInputStream;
import java.io.IOException;
import java.io.InputStreamReader;
import java.net.HttpURLConnection;
import java.net.URL;
import java.util.Calendar;
import java.util.HashMap;
import java.util.Map;
import javax.crypto.Mac;
import javax.crypto.spec.SecretKeySpec;
// import commons-codec-<version>.jar, download from http://commons.apache.org/proper/commons-codec/download_codec.cgi
import org.apache.commons.codec.binary.Base64;
public class IdentifyProtocolV1 {
private String encodeBase64(byte[] bstr) {
Base64 base64 = new Base64();
return new String(base64.encode(bstr));
}
private String encryptByHMACSHA1(byte[] data, byte[] key) {
try {
SecretKeySpec signingKey = new SecretKeySpec(key, "HmacSHA1");
Mac mac = Mac.getInstance("HmacSHA1");
mac.init(signingKey);
byte[] rawHmac = mac.doFinal(data);
return encodeBase64(rawHmac);
} catch (Exception e) {
e.printStackTrace();
}
return "";
}
private String getUTCTimeSeconds() {
Calendar cal = Calendar.getInstance();
int zoneOffset = cal.get(Calendar.ZONE_OFFSET);
int dstOffset = cal.get(Calendar.DST_OFFSET);
cal.add(Calendar.MILLISECOND, -(zoneOffset + dstOffset));
return cal.getTimeInMillis()/1000 + "";
}
private String postHttp(String posturl, Map<String, Object> params, int timeOut) {
String res = "";
String BOUNDARYSTR = "*****2015.03.30.acrcloud.rec.copyright." + System.currentTimeMillis() + "*****";
String BOUNDARY = "--" + BOUNDARYSTR + "\r\n";
String ENDBOUNDARY = "--" + BOUNDARYSTR + "--\r\n\r\n";
String stringKeyHeader = BOUNDARY +
"Content-Disposition: form-data; name=\"%s\"" +
"\r\n\r\n%s\r\n";
String filePartHeader = BOUNDARY +
"Content-Disposition: form-data; name=\"%s\"; filename=\"%s\"\r\n" +
"Content-Type: application/octet-stream\r\n\r\n";
URL url = null;
HttpURLConnection conn = null;
BufferedOutputStream out = null;
BufferedReader reader = null;
ByteArrayOutputStream postBufferStream = new ByteArrayOutputStream();
try {
for (String key : params.keySet()) {
Object value = params.get(key);
if (value instanceof String || value instanceof Integer) {
postBufferStream.write(String.format(stringKeyHeader, key, (String)value).getBytes());
} else if (value instanceof byte[]) {
postBufferStream.write(String.format(filePartHeader, key, key).getBytes());
postBufferStream.write((byte[]) value);
postBufferStream.write("\r\n".getBytes());
}
}
postBufferStream.write(ENDBOUNDARY.getBytes());
url = new URL(posturl);
conn = (HttpURLConnection) url.openConnection();
conn.setConnectTimeout(timeOut);
conn.setReadTimeout(timeOut);
conn.setRequestMethod("POST");
conn.setDoOutput(true);
conn.setDoInput(true);
conn.setRequestProperty("Accept-Charset", "utf-8");
conn.setRequestProperty("Content-type", "multipart/form-data;boundary=" + BOUNDARYSTR);
conn.connect();
out = new BufferedOutputStream(conn.getOutputStream());
out.write(postBufferStream.toByteArray());
out.flush();
int response = conn.getResponseCode();
if (response == HttpURLConnection.HTTP_OK) {
reader = new BufferedReader(new InputStreamReader(conn.getInputStream(), "UTF-8"));
String tmpRes = "";
while ((tmpRes = reader.readLine()) != null) {
if (tmpRes.length() > 0)
res = res + tmpRes;
}
}
} catch (Exception e) {
e.printStackTrace();
} finally {
try {
if (postBufferStream != null) {
postBufferStream.close();
postBufferStream = null;
}
if (out != null) {
out.close();
out = null;
}
if (reader != null) {
reader.close();
reader = null;
}
if (conn != null) {
conn.disconnect();
conn = null;
}
} catch (IOException e) {
e.printStackTrace();
}
}
return res;
}
public String recognize(String host, String accessKey, String secretKey, byte[] queryData, String queryType, int timeout)
{
String method = "POST";
String httpURL = "/v1/identify";
String dataType = queryType;
String sigVersion = "1";
String timestamp = getUTCTimeSeconds();
String reqURL = "http://" + host + httpURL;
String sigStr = method + "\n" + httpURL + "\n" + accessKey + "\n" + dataType + "\n" + sigVersion + "\n" + timestamp;
String signature = encryptByHMACSHA1(sigStr.getBytes(), secretKey.getBytes());
Map<String, Object> postParams = new HashMap<String, Object>();
postParams.put("access_key", accessKey);
postParams.put("sample_bytes", queryData.length + "");
postParams.put("sample", queryData);
postParams.put("timestamp", timestamp);
postParams.put("signature", signature);
postParams.put("data_type", queryType);
postParams.put("signature_version", sigVersion);
String res = postHttp(reqURL, postParams, timeout);
return res;
}
public static void main(String[] args) {
File file = new File("E://sample.wav");
byte[] buffer = new byte[1024 * 1024];
if (!file.exists()) {
return;
}
FileInputStream fin = null;
int bufferLen = 0;
try {
fin = new FileInputStream(file);
bufferLen = fin.read(buffer, 0, buffer.length);
} catch (Exception e) {
e.printStackTrace();
} finally {
try {
if (fin != null) {
fin.close();
}
} catch (IOException e) {
e.printStackTrace();
}
}
System.out.println("bufferLen=" + bufferLen);
if (bufferLen <= 0)
return;
byte[] postDatas = new byte[bufferLen];
System.arraycopy(buffer, 0, postDatas, 0, bufferLen);
IdentifyProtocolV1 a = new IdentifyProtocolV1();
// Replace "###...###" below with your project's host, access_key and access_secret.
// recognize(String host, String accessKey, String secretKey, byte[] queryData, String queryType, int timeout)
String result = a.recognize("###YOUR_HOST###", "###YOUR_KEY###", "###YOUR_SECRET###", postDatas, "audio", 10000);
System.out.println(result);
}
}
Javascript
var url = require('url');
var fs = require('fs');
var crypto = require('crypto');
//npm install request
var request = require('request');
// Replace "###...###" below with your project's host, access_key and access_secret.
var defaultOptions = {
host: '###YOUR_HOST###',
endpoint: '/v1/identify',
signature_version: '1',
data_type:'audio',
secure: true,
access_key: '###YOUR_ACCESS_KEY###',
access_secret: '###YOUR_ACCESS_SECRET###'
};
function buildStringToSign(method, uri, accessKey, dataType, signatureVersion, timestamp) {
return [method, uri, accessKey, dataType, signatureVersion, timestamp].join('\n');
}
function sign(signString, accessSecret) {
return crypto.createHmac('sha1', accessSecret)
.update(Buffer.from(signString, 'utf-8'))
.digest().toString('base64');
}
/**
* Identifies a sample of bytes
*/
function identify(data, options, cb) {
var current_data = new Date();
var timestamp = current_data.getTime()/1000;
var stringToSign = buildStringToSign('POST',
options.endpoint,
options.access_key,
options.data_type,
options.signature_version,
timestamp);
var signature = sign(stringToSign, options.access_secret);
var formData = {
sample: data,
access_key:options.access_key,
data_type:options.data_type,
signature_version:options.signature_version,
signature:signature,
sample_bytes:data.length,
timestamp:timestamp,
}
request.post({
url: "http://"+options.host + options.endpoint,
method: 'POST',
formData: formData
}, cb);
}
function identify_v2(data, options, cb) {
//npm install form-data
var FormData = require('form-data');
//npm install node-fetch
var fetch = require('node-fetch');
var current_data = new Date();
var timestamp = current_data.getTime()/1000;
var stringToSign = buildStringToSign('POST',
options.endpoint,
options.access_key,
options.data_type,
options.signature_version,
timestamp);
var signature = sign(stringToSign, options.access_secret);
var form = new FormData();
form.append('sample', data);
form.append('sample_bytes', data.length);
form.append('access_key', options.access_key);
form.append('data_type', options.data_type);
form.append('signature_version', options.signature_version);
form.append('signature', signature);
form.append('timestamp', timestamp);
fetch("http://"+options.host + options.endpoint,
{method: 'POST', body: form })
.then((res) => {return res.text()})
.then((res) => {cb(res, null)})
.catch((err) => {cb(null, err)});
}
var bitmap = fs.readFileSync('sample.wav');
identify(Buffer.from(bitmap), defaultOptions, function (err, httpResponse, body) {
if (err) console.log(err);
console.log(body);
});
ReactNative
import React from 'react';
import {StyleSheet, Button, View, Text} from 'react-native';
import {Audio} from 'expo-av';
import {FileSystem, Permissions} from 'react-native-unimodules';
import hmacSHA1 from 'crypto-js/hmac-sha1';
import Base64 from 'crypto-js/enc-base64';
import {Buffer} from 'buffer';
export default class MusicRec_Test extends React.Component {
constructor(props) {
super(props);
this.state = {response: ''};
}
async _findSong() {
// Audio.setAudioModeAsync()
const {status} = await Audio.requestPermissionsAsync();
console.log('Current Status ' + status);
const recording = new Audio.Recording();
try {
await Audio.setAudioModeAsync({
playsInSilentModeIOS: true,
allowsRecordingIOS: true,
});
const recordOptions = {
android: {
extension: '.m4a',
outputFormat: Audio.RECORDING_OPTION_ANDROID_OUTPUT_FORMAT_MPEG_4,
audioEncoder: Audio.RECORDING_OPTION_ANDROID_AUDIO_ENCODER_AAC,
sampleRate: 44100,
numberOfChannels: 2,
bitRate: 128000,
},
ios: {
extension: '.wav',
audioQuality: Audio.RECORDING_OPTION_IOS_AUDIO_QUALITY_HIGH,
sampleRate: 8000,
numberOfChannels: 1,
linearPCMBitDepth: 16,
linearPCMIsBigEndian: false,
linearPCMIsFloat: true,
},
};
await recording.prepareToRecordAsync(recordOptions);
await recording.startAsync();
console.log('Recording');
await timeout(8000);
console.log('Done recording');
await recording.stopAndUnloadAsync();
let recordingFile = recording.getURI();
let result = await identify(recordingFile, defaultOptions);
console.log(result);
//return result;
} catch (error) {
console.log(error);
console.log('Error in this!!!!');
}
}
render() {
return (
<View style={styles.container}>
<Button title="Find Song" onPress={this._findSong} />
<Text />
</View>
);
}
}
function timeout(ms) {
return new Promise(resolve => setTimeout(resolve, ms));
}
const defaultOptions = {
host: '<Project Host>',
endpoint: '/v1/identify',
signature_version: '1',
data_type: 'audio',
secure: true,
access_key: '<Project AccessKey>',
access_secret: '<Project SecretKey>',
};
function buildStringToSign(
method,
uri,
accessKey,
dataType,
signatureVersion,
timestamp,
) {
return [method, uri, accessKey, dataType, signatureVersion, timestamp].join(
'\n',
);
}
function signString(stringToSign, accessSecret) {
return Base64.stringify(hmacSHA1(stringToSign, accessSecret));
}
async function identify(uri, options) {
var current_data = new Date();
var timestamp = current_data.getTime() / 1000;
var stringToSign = buildStringToSign(
'POST',
options.endpoint,
options.access_key,
options.data_type,
options.signature_version,
timestamp,
);
let fileinfo = await FileSystem.getInfoAsync(uri, {size: true});
var signature = signString(stringToSign, options.access_secret);
var formData = {
sample: {uri: uri, name: 'sample.wav', type: 'audio/wav'},
access_key: options.access_key,
data_type: options.data_type,
signature_version: options.signature_version,
signature: signature,
sample_bytes: fileinfo.size,
timestamp: timestamp,
};
var form = new FormData();
for (let key in formData) {
form.append(key, formData[key]);
}
let postOptions = {
method: 'POST',
headers: {
'Content-Type': 'multipart/form-data',
},
body: form,
};
console.log(postOptions.body);
let response = await fetch(
'http://' + options.host + options.endpoint,
postOptions,
);
let result = await response.text();
console.log(result);
return result;
}
const styles = StyleSheet.create({
container: {
flex: 1,
backgroundColor: '#fff',
alignItems: 'center',
justifyContent: 'center',
},
});
Ruby
require 'openssl'
require 'base64'
require 'net/http/post/multipart'
# Replace "###...###" below with your project's host, access_key and access_secret.
requrl = "http://###YOUR_HOST###/v1/identify"
access_key = "###YOUR_ACCESS_KEY###"
access_secret = "###YOUR_ACCESS_SECRET###"
http_method = "POST"
http_uri = "/v1/identify"
data_type = "audio"
signature_version = "1"
timestamp = Time.now.utc().to_i.to_s
string_to_sign = http_method+"\n"+http_uri+"\n"+access_key+"\n"+data_type+"\n"+signature_version+"\n"+timestamp
digest = OpenSSL::Digest.new('sha1')
signature = Base64.encode64(OpenSSL::HMAC.digest(digest, access_secret, string_to_sign))
file_name = ARGV[0]
sample_bytes = File.size(file_name)
url = URI.parse(requrl)
File.open(file_name) do |file|
req = Net::HTTP::Post::Multipart.new url.path,
"sample" => UploadIO.new(file, "audio/mp3", file_name),
"access_key" =>access_key,
"data_type"=> data_type,
"signature_version"=> signature_version,
"signature"=>signature,
"sample_bytes"=>sample_bytes,
"timestamp" => timestamp
res = Net::HTTP.start(url.host, url.port) do |http|
http.request(req)
end
puts(res.body)
end