<?php
class HjAuth {
private $apiUrl, $appid, $appkey;
public function __construct($apiUrl, $appid, $appkey) {
$this->apiUrl = rtrim($apiUrl, '/');
$this->appid = $appid;
$this->appkey = $appkey;
}
private function generateSign($params) {
ksort($params);
$str = '';
foreach ($params as $k => $v) {
if ($v !== '' && $v !== null) {
$str .= $k . '=' . $v . '&';
}
}
$str .= 'appkey=' . $this->appkey;
return strtolower(hash_hmac('sha256', $str, $this->appkey));
}
private function request($action, $cardCode, $deviceCode = null) {
$params = [
'appid' => $this->appid,
'card_code' => $cardCode,
'timestamp' => time(),
'nonce' => md5(uniqid())
];
if ($deviceCode) $params['device_code'] = $deviceCode;
$params['sign'] = $this->generateSign($params);
$ch = curl_init();
curl_setopt($ch, CURLOPT_URL, $this->apiUrl . '/' . $action);
curl_setopt($ch, CURLOPT_POST, 1);
curl_setopt($ch, CURLOPT_POSTFIELDS, json_encode($params));
curl_setopt($ch, CURLOPT_RETURNTRANSFER, 1);
curl_setopt($ch, CURLOPT_HTTPHEADER, ['Content-Type: application/json']);
$result = curl_exec($ch);
curl_close($ch);
return json_decode($result, true);
}
public function verify($cardCode, $deviceCode = null) {
return $this->request('verify', $cardCode, $deviceCode);
}
public function activate($cardCode, $deviceCode = null) {
return $this->request('activate', $cardCode, $deviceCode);
}
public function heartbeat($cardCode, $deviceCode = null) {
return $this->request('heartbeat', $cardCode, $deviceCode);
}
public function logout($cardCode, $deviceCode = null) {
return $this->request('logout', $cardCode, $deviceCode);
}
}
<script src="https://cdn.bootcdn.net/ajax/libs/crypto-js/4.1.1/crypto-js.min.js"></script>
<script>
class HjAuth {
constructor(apiUrl, appid, appkey) {
this.apiUrl = apiUrl.replace(/\/$/, '');
this.appid = appid;
this.appkey = appkey;
}
generateSign(params) {
const sortedKeys = Object.keys(params).sort();
let str = '';
sortedKeys.forEach(key => {
if (key !== 'sign' && params[key] !== '' && params[key] !== null && params[key] !== undefined) {
str += key + '=' + params[key] + '&';
}
});
str += 'appkey=' + this.appkey;
return CryptoJS.HmacSHA256(str, this.appkey).toString().toLowerCase();
}
async request(action, cardCode, deviceCode) {
const params = {
appid: this.appid,
card_code: cardCode,
timestamp: Math.floor(Date.now() / 1000),
nonce: Math.random().toString(36).substring(2)
};
if (deviceCode) params.device_code = deviceCode;
params.sign = this.generateSign(params);
const response = await fetch(this.apiUrl + '/' + action, {
method: 'POST',
headers: { 'Content-Type': 'application/json' },
body: JSON.stringify(params)
});
return await response.json();
}
verify(cardCode, deviceCode) { return this.request('verify', cardCode, deviceCode); }
activate(cardCode, deviceCode) { return this.request('activate', cardCode, deviceCode); }
heartbeat(cardCode, deviceCode) { return this.request('heartbeat', cardCode, deviceCode); }
logout(cardCode, deviceCode) { return this.request('logout', cardCode, deviceCode); }
}
</script>
import { Device } from '@capacitor/device';
import { Preferences } from '@capacitor/preferences';
import CryptoJS from 'crypto-js';
class HjAuthApp {
constructor(apiUrl, appid, appkey) {
this.apiUrl = apiUrl;
this.appid = appid;
this.appkey = appkey;
}
async getDeviceCode() {
const stored = await Preferences.get({ key: 'device_code' });
if (stored.value) return stored.value;
const info = await Device.getId();
const deviceCode = 'CAP_' + info.identifier;
await Preferences.set({ key: 'device_code', value: deviceCode });
return deviceCode;
}
generateSign(params) {
const sortedKeys = Object.keys(params).sort();
let str = '';
sortedKeys.forEach(key => {
if (key !== 'sign' && params[key] !== '' && params[key] !== null && params[key] !== undefined) {
str += key + '=' + params[key] + '&';
}
});
str += 'appkey=' + this.appkey;
return CryptoJS.HmacSHA256(str, this.appkey).toString().toLowerCase();
}
async request(action, cardCode) {
const deviceCode = await this.getDeviceCode();
const params = {
appid: this.appid, card_code: cardCode, device_code: deviceCode,
timestamp: Math.floor(Date.now() / 1000), nonce: Math.random().toString(36).substring(2)
};
params.sign = this.generateSign(params);
const response = await fetch(this.apiUrl + '/' + action, {
method: 'POST', headers: { 'Content-Type': 'application/json' }, body: JSON.stringify(params)
});
return await response.json();
}
verify(cardCode) { return this.request('verify', cardCode); }
activate(cardCode) { return this.request('activate', cardCode); }
heartbeat(cardCode) { return this.request('heartbeat', cardCode); }
logout(cardCode) { return this.request('logout', cardCode); }
}
public class HjAuth {
private String apiUrl, appid, appkey, deviceCode;
public HjAuth(Context context, String apiUrl, String appid, String appkey) {
this.apiUrl = apiUrl;
this.appid = appid;
this.appkey = appkey;
SharedPreferences prefs = context.getSharedPreferences("hj_auth", Context.MODE_PRIVATE);
this.deviceCode = prefs.getString("device_code", null);
if (this.deviceCode == null) {
this.deviceCode = "ANDROID_" + Settings.Secure.getString(context.getContentResolver(), Settings.Secure.ANDROID_ID);
prefs.edit().putString("device_code", this.deviceCode).apply();
}
}
private String generateSign(Map<String, String> params) throws Exception {
List<String> keys = new ArrayList<>(params.keySet());
Collections.sort(keys);
StringBuilder sb = new StringBuilder();
for (String key : keys) {
String value = params.get(key);
if (!key.equals("sign") && value != null && !value.isEmpty()) {
sb.append(key).append("=").append(value).append("&");
}
}
sb.append("appkey=").append(appkey);
Mac mac = Mac.getInstance("HmacSHA256");
mac.init(new SecretKeySpec(appkey.getBytes(), "HmacSHA256"));
return new BigInteger(1, mac.doFinal(sb.toString().getBytes())).toString(16);
}
}
import CryptoKit
class HjAuth {
private let apiUrl: String, appid: String, appkey: String
private var deviceCode: String { UserDefaults.standard.string(forKey: "device_code") ?? {
let code = "IOS_" + (UIDevice.current.identifierForVendor?.uuidString ?? UUID().uuidString).replacingOccurrences(of: "-", with: "")
UserDefaults.standard.set(code, forKey: "device_code")
return code
}() }
init(apiUrl: String, appid: String, appkey: String) {
self.apiUrl = apiUrl; self.appid = appid; self.appkey = appkey
}
private func generateSign(_ params: [String: String]) -> String {
let sorted = params.filter { $0.key != "sign" && !$0.value.isEmpty }.sorted { $0.key < $1.key }
var str = sorted.map { "\($0.key)=\($0.value)" }.joined(separator: "&") + "&appkey=" + appkey
let key = SymmetricKey(data: Data(appkey.utf8))
return HMAC<SHA256>.authenticationCode(for: Data(str.utf8), using: key).map { String(format: "%02x", $0) }.joined()
}
}
import 'dart:convert';
import 'package:crypto/crypto.dart';
import 'package:device_info_plus/device_info_plus.dart';
import 'package:shared_preferences/shared_preferences.dart';
class HjAuth {
final String apiUrl, appid, appkey;
String? _deviceCode;
HjAuth({required this.apiUrl, required this.appid, required this.appkey});
Future<String> getDeviceCode() async {
if (_deviceCode != null) return _deviceCode!;
final prefs = await SharedPreferences.getInstance();
final stored = prefs.getString('device_code');
if (stored != null) { _deviceCode = stored; return stored; }
final deviceInfo = DeviceInfoPlugin();
String id = Platform.isAndroid ? (await deviceInfo.androidInfo).id : (await deviceInfo.iosInfo).identifierForVendor ?? '';
_deviceCode = 'FLUTTER_' + id;
await prefs.setString('device_code', _deviceCode!);
return _deviceCode!;
}
String _generateSign(Map<String, dynamic> params) {
final sorted = params.keys.toList()..sort();
final str = sorted.where((k) => k != 'sign' && params[k] != '' && params[k] != null).map((k) => '$k=${params[k]}').join('&');
return Hmac(sha256, utf8.encode(appkey)).convert(utf8.encode('$str&appkey=$appkey')).toString();
}
}