Cordova PhoneGap Ionic
配置 Branch
- Complete your Branch Dashboard


配置应用
- Cordova 和 Ionic
<!-- sample config.xml -->
<widget id="com.eneff.branch.cordovatestbed" version="0.0.1" xmlns="http://www.w3.org/ns/widgets" xmlns:cdv="http://cordova.apache.org/ns/1.0">
<!-- Branch -->
<plugin name="branch-cordova-sdk" spec="^4.0.0" />
<branch-config>
<branch-key value="key_live_ndqptlgXNE4LHqIahH1WIpbiyFlb62J3" />
<uri-scheme value="branchcordova" />
<link-domain value="cordova.app.link" /> <!-- Required app.link domain -->
<link-domain value="cordova-alternate.app.link" /> <!-- Required alternate.app.link domain -->
<ios-team-release value="PW4Q8885U7" />
</branch-config>
<!-- sample config.xml -->
<widget id="com.eneff.branch.cordovatestbed" version="1.0.0" xmlns="http://www.w3.org/ns/widgets" xmlns:gap="http://phonegap.com/ns/1.0">
<!-- Branch -->
<plugin name="branch-cordova-sdk" spec="^4.0.0" />
<branch-config>
<branch-key value="key_live_ndqptlgXNE4LHqIahH1WIpbiyFlb62J3" />
<uri-scheme value="branchcordova" />
<link-domain value="cordova.app.link" /> <!-- Required app.link domain -->
<link-domain value="cordova-alternate.app.link" /> <!-- Required alternate.app.link domain -->
<ios-team-release value="PW4Q8885U7" />
</branch-config>
-
Change the following values to match your Branch Dashboard
-
com.eneff.branch.cordovatestbed
-
key_live_ndqptlgXNE4LHqIahH1WIpbiyFlb62J3
-
branchcordova
-
cordova.app.link
-
PW4Q8885U7
初始化 Branch
- Cordova 和 PhoneGap
// sample index.js
var app = {
initialize: function() {
this.bindEvents();
},
bindEvents: function() {
document.addEventListener('deviceready', this.onDeviceReady, false);
document.addEventListener('resume', this.onDeviceResume, false);
},
onDeviceReady: function() {
app.handleBranch();
},
onDeviceResume: function() {
app.handleBranch();
},
handleBranch: function() {
// Branch initialization
Branch.initSession().then(function(data) {
if (data['+clicked_branch_link']) {
// read deep link data on click
alert('Deep Link Data: ' + JSON.stringify(data));
}
});
}
};
app.initialize();
// sample app.js
angular.module('starter', ['ionic', 'starter.controllers', 'starter.services'])
.run(function($ionicPlatform) {
$ionicPlatform.ready(function() {
if (window.cordova && window.cordova.plugins && window.cordova.plugins.Keyboard) {
cordova.plugins.Keyboard.hideKeyboardAccessoryBar(true);
cordova.plugins.Keyboard.disableScroll(true);
}
if (window.StatusBar) {
StatusBar.styleDefault();
}
// Branch
$ionicPlatform.on('deviceready', function() {
handleBranch();
});
$ionicPlatform.on('resume', function() {
handleBranch();
});
function handleBranch() {
// Branch initialization
Branch.initSession().then(function(data) {
if (data['+clicked_branch_link']) {
// read deep link data on click
alert('Deep Link Data: ' + JSON.stringify(data));
}
});
}
});
})
// ...
// sample app.component.js
import { Component } from '@angular/core';
import { Platform } from 'ionic-angular';
import { StatusBar, Splashscreen } from 'ionic-native';
import { TabsPage } from '../tabs/tabs
@Component({
template: `<ion-nav [root]="rootPage"></ion-nav>`
})
export class MyApp {
rootPage = TabsPage;
constructor(platform: Platform) {
platform.ready().then(() => {
StatusBar.styleDefault();
Splashscreen.hide();
handleBranch();
});
platform.resume.subscribe(() => {
handleBranch();
});
// Branch initialization
const handleBranch = () => {
// only on devices
if (!platform.is('cordova')) { return }
const Branch = window['Branch'];
Branch.initSession().then(data => {
if (data['+clicked_branch_link']) {
// read deep link data on click
alert('Deep Link Data: ' + JSON.stringify(data));
}
});
}
}
}
测试深度链接 iOS
- Create a deep link from the Branch Dashboard
- 从设备中删除您的应用
- Compile your app (
cordova run ios
phonegap run ios
ionic run ios
) - Paste deep link in Apple Notes
- 长按深度链接(不是 3D Touch)
- Click Open in "APP_NAME" to open your app

测试深度链接 Android
- Create a deep link from the Branch Dashboard
- 从设备中删除您的应用
- Compile your app (
cordova run android
phonegap run android
ionic run android
) - Paste deep link in Google Hangouts
- 点击深度链接打开您的应用
实现功能
初始化 Branch 功能
- 将 Branch 加载到您的应用中
- Must be called on
deviceready
andresume
// for development and debugging only
Branch.setDebug(true)
// for GDPR compliance (can be called at anytime)
Branch.disableTracking(true);
// Branch initialization
Branch.initSession().then(function(data) {
if (data['+clicked_branch_link']) {
// read deep link data on click
alert('Deep Link Data: ' + JSON.stringify(data))
}
})
创建内容参考
- The Branch Universal Object encapsulates the thing you want to share (content or user)
- Uses the Universal Object Properties
// only canonicalIdentifier is required
var properties = {
canonicalIdentifier: 'content/123',
canonicalUrl: 'https://example.com/content/123',
title: 'Content 123 Title',
contentDescription: 'Content 123 Description ' + Date.now(),
contentImageUrl: 'http://lorempixel.com/400/400/',
price: 12.12,
currency: 'GBD',
contentIndexingMode: 'private',
contentMetadata: {
custom: 'data',
testing: 123,
this_is: true
}
}
// create a branchUniversalObj variable to reference with other Branch methods
var branchUniversalObj = null
Branch.createBranchUniversalObject(properties).then(function (res) {
branchUniversalObj = res
alert('Response: ' + JSON.stringify(res))
}).catch(function (err) {
alert('Error: ' + JSON.stringify(err))
})
创建深度链接
- 创建带有封装数据的深度链接 URL
- Needs a Branch Universal Object
- Uses Deep Link Properties
- Validate with the Branch Dashboard
// optional fields
var analytics = {
channel: 'facebook',
feature: 'onboarding',
campaign: 'content 123 launch',
stage: 'new user',
tags: ['one', 'two', 'three']
}
// optional fields
var properties = {
$desktop_url: 'http://www.example.com/desktop',
$android_url: 'http://www.example.com/android',
$ios_url: 'http://www.example.com/ios',
$ipad_url: 'http://www.example.com/ipad',
$match_duration: 2000,
custom_string: 'data',
custom_integer: Date.now(),
custom_boolean: true
}
branchUniversalObj.generateShortUrl(analytics, properties).then(function (res) {
alert('Response: ' + JSON.stringify(res.url))
}).catch(function (err) {
alert('Error: ' + JSON.stringify(err))
})
分享深度链接
- 生成 Branch 深度链接,并通过用户选择的渠道对其进行标签
- Needs a Branch Universal Object
- Uses Deep Link Properties
// optional fields
var analytics = {
channel: 'facebook',
feature: 'onboarding',
campaign: 'content 123 launch',
stage: 'new user',
tags: ['one', 'two', 'three']
}
// optional fields
var properties = {
$desktop_url: 'http://www.example.com/desktop',
custom_string: 'data',
custom_integer: Date.now(),
custom_boolean: true
}
var message = 'Check out this link'
// optional listeners (must be called before showShareSheet)
branchUniversalObj.onShareSheetLaunched(function (res) {
// android only
console.log(res)
})
branchUniversalObj.onShareSheetDismissed(function (res) {
console.log(res)
})
branchUniversalObj.onLinkShareResponse(function (res) {
console.log(res)
})
branchUniversalObj.onChannelSelected(function (res) {
// android only
console.log(res)
})
// share sheet
branchUniversalObj.showShareSheet(analytics, properties, message)
读取深度链接
- 从深度链接中提取 Branch 数据
- 最佳做法是从
listener
(to prevent a race condition) - Returns deep link properties
- Listener
// Branch initialization within your deviceready and resume
Branch.initSession().then(function success(res) {
if (res["+clicked_branch_link"]) {
alert("Open app with a Branch deep link: " + JSON.stringify(res));
// Branch quick link: https://cordova.app.link/uJcOH1IFpM
// Branch web link: https://cordova-alternate.app.link/uJcOH1IFpM
// Branch dynamic link: https://cordova.app.link?tags=one&tags=two&tags=three&channel=Copy&feature=onboarding&stage=new+user&campaign=content+123+launch&type=0&duration=0&source=android&data
// Branch uri scheme: branchcordova://open?link_click_id=link-500015444967786346
// Branch android intent: intent://open?link_click_id=518106399270344237#Intent;scheme=looprocks;package=com.eneff.branch.cordovatestbed;S.browser_fallback_url=https%3A%2F%2Fcordova.app.link%2FuJcOH1IFpM%3F__branch_flow_type%3Dchrome_deepview%26__branch_flow_id%3D518106399312287278;S.market_referrer=link_click_id-518106399270344237%26utm_source%3DCopy%26utm_campaign%3Dcontent%20123%20launch%26utm_feature%3Donboarding;S.branch_data=%7B%22~feature%22%3A%22onboarding%22%2C%22this_is%22%3A%22true%22%2C%22custom_string%22%3A%22data%22%2C%22testing%22%3A%22123%22%2C%22%24publicly_indexable%22%3A%22false%22%2C%22%24desktop_url%22%3A%22http%3A%2F%2Fwww.example.com%2Fdesktop%22%2C%22%24one_time_use%22%3Afalse%2C%22custom_object%22%3A%22%7B%5C%5C%5C%22random%5C%5C%5C%22%3A%5C%5C%5C%22dictionary%5C%5C%5C%22%7D%22%2C%22~id%22%3A%22517795540654792902%22%2C%22~campaign%22%3A%22content%20123%20launch%22%2C%22%2Bclick_timestamp%22%3A1524764418%2C%22%2Burl%22%3A%22https%3A%2F%2Fcordova.app.link%2FuJcOH1IFpM%22%2C%22custom_boolean%22%3A%22true%22%2C%22custom%22%3A%22data%22%2C%22source%22%3A%22android%22%2C%22%24og_image_url%22%3A%22http%3A%2F%2Florempixel.com%2F400%2F400%2F%22%2C%22%2Bdomain%22%3A%22cordova.app.link%22%2C%22custom_integer%22%3A%221524690301794%22%2C%22~tags%22%3A%5B%22one%22%2C%22two%22%2C%22three%22%5D%2C%22custom_array%22%3A%22%5B1%2C2%2C3%2C4%2C5%5D%22%2C%22~channel%22%3A%22Copy%22%2C%22~creation_source%22%3A2%2C%22%24canonical_identifier%22%3A%22content%2F123%22%2C%22%24og_title%22%3A%22Content%20123%20Title%22%2C%22%24og_description%22%3A%22Content%20123%20Description%201524690296449%22%2C%22%24identity_id%22%3A%22453670943617990547%22%2C%22~stage%22%3A%22new%20user%22%2C%22%2Bclicked_branch_link%22%3Atrue%2C%22%2Bmatch_guaranteed%22%3Atrue%2C%22%2Bis_first_session%22%3Afalse%7D;B.branch_intent=true;end
// Branch android app link (device controlled): https://cordova.app.link/uJcOH1IFpM
// Branch ios universal link (device controlled): https://cordova.app.link/uJcOH1IFpM
} else if (res["+non_branch_link"]) {
alert("Open app with a non Branch deep link: " + JSON.stringify(res));
// Competitor uri scheme: anotherurischeme://hello=world
} else {
alert("Open app organically");
// Clicking on app icon or push notification
}
})
.catch(function error(err) {
logger(err, true);
});
- 最新数据
Branch.getLatestReferringParams().then(function(res) {
alert('Response: ' + JSON.stringify(res))
}).catch(function(err) {
alert('Error: ' + JSON.stringify(err))
})
- First data
Branch.getFirstReferringParams().then(function(res) {
alert('Response: ' + JSON.stringify(res))
}).catch(function(err) {
alert('Error: ' + JSON.stringify(err))
})
NativeLink™ Deferred Deep Linking (iOS Only)
- Use iOS pasteboard to enable deferred deep linking via Branch NativeLink™
先决条件
Make sure the underlying iOS SDK Version is v1.39.4+
To use this feature you must:
- Enable NativeLink™ Deep Linking in the Branch Dashboard Configuration tab
or- Manually configure your Branch Link to use
$ios_clipboard_deepview
Implement one of the pasteboard opt-in options in the native iOS SDK code.
Create QR Code
- Set your Qr Code Settings
- Set your Analytics and Link Properties
- Use getBranchQRCode() to create a QR code.
var qrCodeSettings = {
width: 2000,
codeColor: "#3b2016",
backgroundColor: "#a8e689",
centerLogo: "https://cdn.britannica.com/95/156695-131-FF89C9FA/oak-tree.jpg",
margin: 4,
imageFormat: "PNG"
};
var analytics = {
channel: "facebook",
feature: "onboarding",
campaign: "content 123 launch",
stage: "new user",
tags: ["one", "two", "three"],
alias: document.getElementById("alias").value
};
var properties = {
$desktop_url: "http://www.example.com/desktop",
$android_url: "http://www.example.com/android",
$ios_url: "http://www.example.com/ios",
$ipad_url: "http://www.example.com/ipad",
$deeplink_path: "content/123",
$match_duration: 2000,
custom_string: "data",
custom_integer: Date.now(),
custom_boolean: true
};
if (branchUniversalObj === null) {
alert("Need to Generate Branch Universal Object");
return;
}
Branch
.getBranchQRCode(qrCodeSettings, branchUniversalObj, analytics, properties)
.then(function success(res) {
document.getElementById("qrCodeImage").src = "data:image/png;base64, " + res;
})
.catch(function error(err) {
alert(err, true);
});
Learn more from our QR Code API
前往内容
- 在此方法中处理
Branch.initSession()
- Branch 允许您将任何自定义 key-value 从 URL 传递到您的应用。使用此数据导航到内容,显示个性化的欢迎屏幕,登录用户,提供促销等。
Branch.initSession().then(function(data) {
if (data['+clicked_branch_link']) {
// option 1: save to model to be used later
window.localStorage['branchData'] = data;
// option 2: navigate to page
window.location.href = '#/content/123'
// option 3: display data
alert(JSON.stringify(data));
}
});
展示内容
- List content on iOS Spotlight
- Needs a Branch Universal Object
branchUniversalObj.listOnSpotlight().then(function (res) {
alert('Response: ' + JSON.stringify(res))
}).catch(function (err) {
alert('Error: ' + JSON.stringify(err))
})
追踪内容
- 追踪一段内容的查看次数
- Needs a Branch Universal Object
- Validate with the Branch Dashboard
branchUniversalObj.registerView().then(function (res) {
alert('Response: ' + JSON.stringify(res))
}).catch(function (err) {
alert('Error: ' + JSON.stringify(err))
})
追踪用户
- Sets the identity of a user (ID, UUID, etc) for events, deep links, and referrals
- Validate with the Branch Dashboard
var userId = '123456'
Branch.setIdentity(userId).then(function (res) {
alert('Response: ' + JSON.stringify(res))
}).catch(function (err) {
alert('Error: ' + JSON.stringify(err.message))
})
- 删除用户身份
Branch.logout().then(function (res) {
alert('Response: ' + JSON.stringify(res))
}).catch(function (err) {
alert('Error: ' + JSON.stringify(err.message))
})
追踪事件
- 注册自定义事件
- Events named
open
,close
,install
, andreferred session
are Branch restricted - Best to Track users before Track events to associate a custom event to a user
- Validate with the Branch Dashboard
var eventName = 'clicked_on_this';
var metadata = { 'custom_dictionary': 123, 'anything': 'everything' };
Branch.sendBranchEvent(eventName, metadata);
var eventName = 'clicked_on_this';
Branch.sendBranchEvent(eventName);
追踪 commerce
- 注册自定义 Commerce Event
- Uses Track commerce properties for
Currency
andCategory
- Validate with the Branch Dashboard
Branch.getStandardEvents().then(function success(res) {
var event = res.STANDARD_EVENT_ADD_TO_CART;
var properties = {
transactionID: '12344555',
currency: 'USD',
revenue: 1.5,
shipping: 10.2,
tax: 12.3,
coupon: 'test_coupon',
affiliation: 'test_affiliation',
description: 'Test add to cart event',
searchQuery: 'test keyword',
customData: {
"Custom_Event_Property_Key1": "Custom_Event_Property_val1",
"Custom_Event_Property_Key2": "Custom_Event_Property_val2"
},
contentMetadata: [
{
"$content_schema": "COMMERCE_PRODUCT",
"$og_title": "Nike Shoe",
"$og_description": "Start loving your steps",
"$og_image_url": "http://example.com/img1.jpg",
"$canonical_identifier": "nike/1234",
"$publicly_indexable": false,
"$price": 101.2,
"$locally_indexable": true,
"$sku": "1101123445",
"$product_name": "Runner",
"$product_brand": "Nike",
"$product_category": "Sporting Goods",
"$product_variant": "XL",
"$creation_timestamp": 1499892854966
},
{
"$content_schema": "COMMERCE_PRODUCT",
"$og_title": "Adidas Shoe",
"$og_description": "Start loving your steps",
"$og_image_url": "http://example.com/img1.jpg",
"$canonical_identifier": "adidas/1234",
"$publicly_indexable": false,
"$price": 90.2,
"$locally_indexable": true,
"$sku": "1101123445",
"$product_name": "Runner",
"$product_brand": "Adidas",
"$product_category": "Sporting Goods",
"$product_variant": "XL",
"$creation_timestamp": 1499892854967
}
],
};
Branch.sendBranchEvent(event, properties);
}).catch(function error(err) {
alert("Get Standard Event " + err);
});
排查问题
测试:Key Points
- Need to select
"app uses IDFA or GAID"
when publishing your app - Best to enable Deepviews (Testing: Supported Platforms)
- Mobile browser capability:
Android 4.4.4+
,Safari 8+
,Chrome 32+
,Firefox 29+
测试:可选的 App Config
- 自定义链接域的附加配置,模拟安装,唯一 Bundle ID 等
<!-- sample config.xml -->
<widget id="com.eneff.branch.cordovatestbed" version="1.0.0" xmlns="http://www.w3.org/ns/widgets" xmlns:cdv="http://cordova.apache.org/ns/1.0">
<!-- Branch -->
<plugin name="branch-cordova-sdk" spec="^4.0.0" /> <!-- optional spec -->
<branch-config>
<branch-key value="key_live_ndqptlgXNE4LHqIahH1WIpbiyFlb62J3" />
<uri-scheme value="branchcordova" />
<link-domain value="yourcustomdomain.com" />
<link-domain value="cordova.app.link" /> <!-- optional previous link domain -->
<link-domain value="bnc.lt" /> <!-- optional previous link domain -->
<ios-team-release value="PW4Q8885U7" /> <!-- required if iOS app -->
<ios-team-debug value="FG35JLLMXX" /> <!-- optional -->
<android-prefix value="/WSuf" /> <!-- optional (for bnc.lt) -->
<android-testmode value="true" /> <!-- optional (simulate installs) -->
</branch-config>
<widget ios-CFBundleIdentifier="com.eneff.branch.cordovatestbedios" android-packageName="com.eneff.branch.cordovatestbedandroid" version="1.0.0" xmlns="http://www.w3.org/ns/widgets" xmlns:cdv="http://cordova.apache.org/ns/1.0">
测试:Branch 分析
- Whenever a user
clicks
on a deep link and opens the app, and will trigger either aninstall
or anopen
installs
代表 Branch 首次识别 app_id 和 device_idinstalls
代表新的应用用户以及您的 Branch 深度链接的成功率installs
不代表 App Store 下载non-Branch installs
为安装在 Branch 深度链接点击之外的opens
为非安装- If a user uninstalls and reinstalls the app, this will be an
open
because Branch recognizes the device - If a user has the app and clicks a Branch deep link, this will be an
open
because the user is not new
测试:模拟安装
- 删除您的应用
- [iOS] iPhone Device->Settings->Privacy->Advertising->Reset Advertising Identifier->Reset Identifier
- [Android] Add
<android-testmode value="true" />
to yourconfig.xml
(Testing: Optional App Config) - 添加
Branch.setDebug(true);
beforeBranch.initSession();
(Initialize Branch Features) - Click on a deep link to navigate to your
$fallback_url
because your app is not installed - 安装您的应用
- 打开您的应用
- Read from
Branch.initSession().then(data)
for+is_first_session = true
测试:支持的平台
- 支持 Branch 深度链接的应用
App | iOS | 细节 | Android | 细节 |
---|---|---|---|---|
Facebook NewsFeed | ✅ | Works when DeepViews are enabled | ✅ | |
Facebook Messenger | ✅ | Works when DeepViews are enabled | ✅ | |
✅ | ✅ | |||
✅ | Works when DeepViews are enabled | ✅ | ||
Slack | ✅ | ✅ | ||
Chrome 地址栏 | 🅾 | 🅾 | ||
Chrome 网页 | ✅ | ✅ | ||
FireFox 地址栏 | 🅾 | 🅾 | ||
FireFox 网页 | ✅ | ✅ | ||
Safar i地址栏 | 🅾 | |||
Safari 网页 | ✅ | |||
✅ | Works when DeepViews are enabled | ✅ | ||
✅ |
| ✅ |
| |
Hangouts | ✅ | ✅ | ||
iMessage | ✅ | |||
苹果邮件 | ✅ | |||
Gmail | ✅ | ✅ |
链接数据:Universal Object 属性
Key | 默认 | 用途 | 链接属性 |
---|---|---|---|
| (必需) 这是内容的标识符,将帮助 Branch 在同一事物的许多实例之间进行重复数据删除。合适的选项:具有路径的网站或具有实体标识符的数据库 |
| |
| 规范网址,用于SEO |
| |
| 内容的名称 |
| |
| 内容说明 |
| |
| 内容的图片网址。必须是绝对路径 |
| |
| 商品价格 |
| |
| 表示价格的货币,采用ISO 4217货币代码 |
| |
|
| 可以设置为 |
|
| 任何自定义键值数据,例如 |
链接数据:深度链接属性
- For Create Deep Link and Share Deep Link
- 分析工具
Key | 默认 | 用途 |
---|---|---|
渠道 | 您可以使用渠道来标记链接到达用户的路径。例如,链接可标记为 | |
功能 | 这是链接可能与您的应用相关的功能。例如,如果您构建了引荐程序,则可以使用 “referral” 功能标记链接 | |
Campaign | 使用此字段按实际 Campaign(营销活动)生成链接。例如,当您启动了一项新功能或产品,并希望围绕该功能设立 Campaign 时,可以使用此功能。 | |
阶段 | 生成链接时,可使用此选项对用户的进度或类别进行分类。例如,如果您的邀请系统可以在1级,3级和5级上访问,则您可以使用此参数来区分在不同级别上生成的链接 | |
标签 | 这是具有无限值的自由格式条目 | |
alias | Specify a link alias in place of the standard encoded short URL e.g. | |
type |
| 设置为 |
-
属性
- 自定义数据
Key | 值 | 用途 |
---|---|---|
随机 |
| key-values 对组 |
你好 |
| key-values 对组 |
custom_data |
| key-values 对组 |
- Redirection
Key | 默认 | 用途 |
---|---|---|
$fallback_url | 更改所有平台的重定向 endpoint—因此您不必按平台启用它。需要注意的是 Branch 将所有机器人导向到这个 URL,其中 覆盖任何 OG 标签 中输入的链接。系统范围的默认 URL(在 Link Settings 中设置) | |
$ desktop_url | 更改桌面上 Text-Me-The-App 页面的重定向终结点(在 Link Settings 中设置) | |
$ios_url | 更改您应用的 iOS App Store 页面的重定向终结点(在 Link Settings 中设置) | |
$ipad_url | 更改 iPad 的重定向端点 | |
$android_url | 更改您应用的 Android Play 商店页面的重定向端点(在 Link Settings 中设置) | |
$windows_phone_url | 更改 Windows 操作系统和手机的默认 URL 重定向终结点(在 Link Setting 中设置) | |
$blackberry_url | 更改 Blackberry OS BlackBerry 默认URL的重定向终结点(在 Link Setting 中设置) | |
$fire_url | 更改 Amazon Fire OS Fire 默认 URL 的重定向终端节点(在 Link Setting 中设置) | |
$ios_wechat_url | 更改 iOS 设备上微信的重定向 endpoint | |
$android_wechat_url | 更改 Android 设备上微信的重定向终结点 | |
$after_click_url | 主点击重定向完成后,URL 重定向到 | |
$web_only |
| 强制打开 |
- Deep Link
Key | 默认 | 用途 |
---|---|---|
$deeplink_path |
| 设置所有平台的深度链接路径—因此您不必按平台启用它。当 Branch SDK 收到带有此参数集的链接时,它将自动加载其中包含的自定义 URI 路径 |
$android_deeplink_path | 设置 Android 应用的深度链接路径当 Branch SDK 收到具有此参数集的链接时,它将自动加载包含在其中的自定义 URI 路径 | |
$ios_deeplink_path | 设置 iOS 应用的深度链接路径。当 Branch SDK 收到带有此参数集的链接时,它将自动加载其中包含的自定义 URI 路径 | |
$match_duration |
| 使您可以控制概率建模超时(点击等待应用打开的时间),也称为归因窗口。以秒为单位 |
$always_deeplink |
| 设置为 |
$ios_redirect_timeout |
| 控制客户端 JS 在尝试打开应用后重定向到 App Store 之前的等待超时,以毫秒为单位 |
$android_redirect_timeout |
| 控制客户端 JS 在尝试打开应用后重定向到 Play Store 之前等待的超时。以毫秒为单位 |
$one_time_use |
| 设置为 |
$custom_sms_text | 发送给 SMS 链接的文本,供桌面点击此链接。必须包含 | |
$marketing_title | The Marketing Title for the deep link in the Marketing Dashboard |
- Content
Key | 默认 | 用途 |
---|---|---|
$publicly_indexable |
| 无法在此处修改。需要由 Branch Universal Object 设置 |
$keywords | 此内容应作为关键字的关键词。只需使用您想要使用的关键字分配一个 string 数组 | |
$canonical_identifier | 这是内容的标识符,可帮助 Branch 在同一事物的许多实例之间进行重复数据删除。合适的选项:具有路径的网站或具有实体标识符的数据库 | |
$exp_date |
| 无法在此处修改。需要由 Branch Universal Object 设置。必须是纪元时间戳,以毫秒为单位 |
$content_type | 这是存在的内容类型的标签。 Apple 建议您按照此处所述使用统一类型的标识符 |
- DeepView
Key | 默认 | 用途 |
---|---|---|
$ios_deepview |
| 用于 iOS 的 Deepview 模板的名称 |
$android_deepview |
| 用于 Android 的 Deepview 模板的名称 |
$desktop_deepview |
| 用于桌面的 Deepview 模板的名称 |
- Open Graph
Key | 默认 | 用途 |
---|---|---|
$og_title | 设置链接的标题,以使其在社交媒体显示中看到 | |
$og_description | 设置链接的描述,以便在社交媒体显示中看到 | |
$og_image_url | 设置链接的图像,使其在社交媒体显示中看到 | |
$og_image_width | 为社交媒体显示设置图像的宽度(以像素为单位) | |
$og_image_height | 设置图像高度(以像素为单位)以显示社交媒体 | |
$og_video | 设置视频,使其在社交媒体显示中看到 | |
$og_url | 设置链接的 base URL,因为它将在社交媒体显示中看到 | |
$og_type | 设置自定义卡格式链接的类型,因为它将在社交媒体显示中看到 | |
$og_redirect | (高级,不建议使用)设置自定义 URL,我们将社交媒体 robot 重定向到该 URL,以便获得所有适当的标签 | | |
$og_app_id | (很少使用)设置应用ID标签 |
- Twitter
Key | 默认 | 用途 |
---|---|---|
$twitter_card | 设置链接的 Twitter 卡类型 | |
$twitter_title | 设置 Twitter 卡的标题 | |
$twitter_description | 设置 Twitter 卡的描述 | |
$twitter_image_url | 设置 Twitter 卡的图片网址 | |
$twitter_site | 设置 Twitter 网站 | |
$twitter_app_country | 设置应用卡的应用国家/地区 | |
$twitter_player | Set the video player’s URL. Defaults to the value of | |
$twitter_player_width | 设置播放器的宽度(以像素为单位) | |
$twitter_player_height | 设置播放器的高度(以像素为单位) |
链接数据:商业属性
-
For Track commerce
-
分类目录
值 | 类别 | 值 | 类别 |
---|---|---|---|
| Animals & Pet Supplies |
| Home & Garden |
| Apparel & Accessories |
| Luggage & Bags |
| Arts & Entertainment |
| Mature |
| Baby & Toddler |
| Media |
| Business & Industrial |
| Office Supplies |
| Camera & Optics |
| Religious & Ceremonial |
| Electronics |
| Software |
| Food, Beverage & Tobacco |
| Sporting Goods |
| Furniture |
| Toys & Games |
| Hardware |
| Vehicles & Parts |
| Health & Beauty |
- 货币
值 | 货币 | 值 | 货币 | 值 | 货币 |
---|---|---|---|---|---|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| ||
|
|
|
|
链接数据:Mixpanel 集成
- 如果已安装插件,则与 Mixpanel 同步
Branch.setRequestMetadata("$mixpanel_distinct_id", "123");
编译:Cordova 依赖项
- Node
/usr/bin/ruby -e "$(curl -fsSL https://raw.githubusercontent.com/Homebrew/install/master/install)";
brew update;
brew install node;
-
Xcode
- Install Xcode
- 打开 Xcode->同意 SDK 许可协议
- Open Xcode -> Create new Xcode project -> Run simulator -> 在 Mac 上同意运行开发人员模式
-
Android Studio
- Read instructions
- Install JVM
- Install Android Studio
- Open Android Studio -> configure -> appearance/system settings/android sdk -> android 6.0 -> Okay
- Open Android Studio -> New project -> ... -> Run -> Create new emulator -> Nexus 6p 23 -> Finish
# add to ~/.bash_profile
export ANDROID_HOME=$HOME/Library/Android/sdk
export PATH=$ANDROID_HOME/tools:$PATH
export PATH=$ANDROID_HOME/platform-tools:$PATH
source ~/.bash_profile;
android update sdk;
- 安装 Android SDK build-tools 24.0.1
- 生成 Android Keystore
keytool -genkeypair -dname "cn=Full Name, ou=Business Unit, o=Company, c=US" -alias release -keypass aaa111 -keystore release.keystore -storepass aaa111 -validity 10000
keytool -list -v -keystore release.keystore
-
Genymotion [可选]
- Install Virtual Box
- Install Genymotion
- Genymotion -> Add virtual device -> Google Nexus 6P - 6.0.0 - API 23 -> Next
编译:显示控制台日志
-
iOS 模拟器
cordova run ios;
- Safari -> Preferences -> Advance -> Show Develop menu in menu bar
- Safari -> Develop -> Simulator -> index.html -> Console
- 可能需要断开并重新连接设备
- 可能需要打开 Xcode 并更新配置文件
-
iOS Xcode
cordova plugin add cordova-plugin-console;
cordova build ios;
- Xcode->
APP_LOCATION/platforms/ios/APP_NAME.Xcodeproj
- Xcode -> App -> General -> Signing -> Team
- Xcode -> Product -> Run
- Xcode -> View -> Debug Area -> Activate Console
-
Android 设备
- 连接设备
cordova run android;
- Chrome ->
[chrome://inspect/#devices](chrome://inspect/#devices)
-> Console
-
Android Genymotion
- Genymotion ->Start
cordova run android;
- Chrome ->
[chrome://inspect/#devices](chrome://inspect/#devices)
-> Console
编译:更新 Branch SDK
- 获得最新的改进和功能
# terminal
cordova plugin remove io.branch.sdk
cordova plugin remove branch-cordova-sdk
<!-- config.xml -->
<plugin name="branch-cordova-sdk" spec="^4.0.0" />
编译:不兼容
-
以下插件不适用于 Branch SDK
-
Branch SDK 也不支持 PhoneGap Build,因为我们需要插件 hooks 来启用 entitlement,Universal Links,App Links 和 URI scheme 重定向,但是PhoneGap Build 不允许插件 hooks。
-
安装了 “branch-cordova-sdk” 插件和 “cordova-plugin-siri-shortcuts” 插件后,深度链接就会中断。在 Branch 插件之后安装 siri 快捷方式插件时,这似乎最经常发生。
- 解决方案
- Using a modified version of the
AppDelegate+SiriShortcuts
Category to include Branch. This version only works if both Branch and SiriShortcuts is present. - From within the Xcode workspace, locate
AppDelegate+BranchSDK.m
. Either remove it or ignore it. - From within the Xcode workspace, locate
AppDelegate+SiriShortcuts.m
. This is the file we want to modify. - Update
AppDelegate+SiriShortcuts.m
to call Branch SDK. This version should work when dropped in with the current release of both SDKs.
- Using a modified version of the
- 解决方案
#import "AppDelegate+SiriShortcuts.h"
#import <objectivec/runtime.h>
#import "BranchNPM.h"
#ifdef BRANCH_NPM
#import "Branch.h"
#else
#import <Branch/Branch.h>
#endif
static void * UserActivityPropertyKey = &UserActivityPropertyKey;
@implementation AppDelegate (siriShortcuts)
- (NSUserActivity *)userActivity {
return objectivec_getAssociatedObject(self, UserActivityPropertyKey);
}
- (void)setUserActivity:(NSUserActivity *)activity {
objectivec_setAssociatedObject(self, UserActivityPropertyKey, activity, objectivec_ASSOCIATION_RETAIN_NONATOMIC);
}
- (BOOL)application:(UIApplication *)application continueUserActivity:(NSUserActivity *)userActivity restorationHandler:(void (^)(NSArray *))restorationHandler {
// SiriShortcuts code
NSString *bundleIdentifier = [[NSBundle mainBundle] bundleIdentifier];
if ([userActivity.activityType isEqualToString:[NSString stringWithFormat:@"%@.shortcut", bundleIdentifier]]) {
self.userActivity = userActivity;
}
// Respond to Universal Links
if (![[Branch getInstance] continueUserActivity:userActivity]) {
// send unhandled URL to notification
if ([userActivity.activityType isEqualToString:NSUserActivityTypeBrowsingWeb]) {
[[NSNotificationCenter defaultCenter] postNotification:[NSNotification notificationWithName:@"BSDKPostUnhandledURL" object:[userActivity.webpageURL absoluteString]]];
}
}
return YES;
}
// Respond to URI scheme links
- (BOOL)application:(UIApplication *)app openURL:(NSURL *)url options:(NSDictionary<UIApplicationOpenURLOptionsKey,id> *)options {
// pass the url to the handle deep link call
if (![[Branch getInstance] application:app openURL:url options:options]) {
// do other deep link routing for the Facebook SDK, Pinterest SDK, etc
[[NSNotificationCenter defaultCenter] postNotification:[NSNotification notificationWithName:CDVPluginHandleOpenURLNotification object:url]];
// send unhandled URL to notification
[[NSNotificationCenter defaultCenter] postNotification:[NSNotification notificationWithName:@"BSDKPostUnhandledURL" object:[url absoluteString]]];
}
return YES;
}
// Respond to Push Notifications
- (void)application:(UIApplication *)application didReceiveRemoteNotification:(NSDictionary *)userInfo {
@try {
[[Branch getInstance] handlePushNotification:userInfo];
}
@catch (NSException *exception) {
[[NSNotificationCenter defaultCenter] postNotification:[NSNotification notificationWithName:@"BSDKPostUnhandledURL" object:userInfo]];
}
}
@end
编译:Cordova 错误
从 SDK 2.5+迁移到3.0+
// Branch initialization
- Branch.initSession(function(data) {
+ Branch.initSession().then(function(data) {
if (data["+clicked_branch_link"]) {
// read deep link data on click
alert("Deep Link Data: " + JSON.stringify(data));
}
});
仅设备
-
错误
ORIGINAL EXCEPTION: Branch is not defined
ReferenceError: Branch is not defined
-
解决方案
- Branch 将打开并安装您的应用,因此您无法在桌面浏览器或模拟器中模拟Branch
// Ionic 2/3 - running on browser instead of device
if (!platform.is('cordova')) { return }
Branch.userCompletedAction('did_this')
// Ionic 2/3 - missing Branch import
const Branch = window['Branch'];
配置文件丢失
- 错误
** ARCHIVE FAILED **
The following build commands failed:
Check dependencies
(1 failure)
Error: Error code 65 for command: xcodebuild with args: -xcconfig,cordova/build-debug.xcconfig,-workspace,Branch Testing.xcworkspace,-scheme,Branch Testing,-configuration,Debug,-destination,generic/platform=iOS,-archivePath,Branch Testing.xcarchive,archive,CONFIGURATION_BUILD_DIR=build/device,SHARED_PRECOMPS_DIR=build/sharedpch
No profiles for 'com.eneff.branch.cordova_testbed' were found
-
解决方案
- Fix by opening your app in
Xcode
and launch from there (to select aProvisioning Profile
)
- Fix by opening your app in
无效的 Bundle ID
- 错误
An invalid value 'XC com eneff branch cordova_testbed' was provided for the parameter 'appIdName'.
Error: Error code 1 for command: /gradlew with args: cdvBuildDebug,-b,/build.gradle,-Dorg.gradle.daemon=true,-Pandroid.useDeprecatedNdk=true
-
解决方案
- Don't use
cordova
,hyphens
(Android), orunderscores
(iOS) in your bundle id (widget id)
- Don't use
未找到文件
- 错误
Branch.h not found
-
解决方案
-
如果这是您看到的唯一错误,则可以通过升级依赖项来解决。确保您使用的是此插件的4.0.1或更高版本,并且已将 Xcode,Cordova 和其他依赖项(下面列出)更新为最新版本。由于 CocoaPods 和 cordova-ios 无法解决依赖关系而导致的此错误后来被修复。
-
有时,当 Pod 项目中发生构建错误时,就会发生此错误。由于 Branch 通常是按字母顺序排列的第一个 Pod,因此在尝试构建主项目时会显示为错误(因为 Pod 没有被构建),即使真正的错误在其他地方也是如此。确保阅读您的构建日志以查找阻止构建 Pod 项目的原始错误。
-
使用 Pod 构建失败
-
iOS 构建因 Pod 和 CONFIGURATION_BUILD_DIR 配置而失败
-
Command-line builds result in the above error. Please see the section below Compiling: Capacitor for the full list of up-to-date dependencies needed for CLI builds to work.
编译:Cordova 8
- 该插件的版本4.1.x与 Cordova 8 兼容,但是您需要在 config.xml 文件中添加一些字段:
- Cordova 8 无法正确支持 CocoaPods,此插件的4.x版本利用了 CocoaPods。
- 此插件不能同时包含两个版本的 Pod 说明(在 Cordova 8 和 Cordova 9 之间进行了更改)。我们选择包含 Cordova 9 版本。
- 为了支持 Cordova 8 对 CocoaPods 的处理,您必须安装一个额外的 Cordova 插件以正确合并我们的 CocoaPod(从2020.02.10 开始的“ Branch” v.0.31.3)
- Install the plugin cordova-plugin-cocoapods-support
- 该插件不会向您的应用添加任何代码,严格来说,这是在构建应用之前创建Podfile 的 Cordova hooks。
- Add the following lines to the
widget/platform[name="ios"]
path in config.xml:
<preference name="pods_ios_min_version" value="<YOUR MINIMUM VALUE>" />
<pod name="Branch" spec="~> 0.31.3" />
- 更换
<YOUR MINIMUM VALUE>
with the minimum iOS version your app requires, e.g. "8" or "10.0" or "11.4" - 运行
cordova prepare ios
again and ensure you see console output similar to
Searching for new pods
Checking config.xml for pods.
config.xml requires pod: Branch
Installing pods
Sit back and relax this could take a while.
- Provided that the dependencies listed in the next section are up to date (see Compiling: Capacitor), you should also be able to do
cordova build ios
without issue.
编译:Capacitor
- 该插件的版本4.1.0可与 Ionic 4 + Cordova 和 Ionic 4 + Capacitor 一起使用,但需注意以下几点:
- 我们强烈建议 Node> = 10.15。Note 8可能可用,但未经测试。
- 对于两个 Cordova 和 Capacitor,您必须使用 Xcode> = 11.1,CocoaPods> = 1.8.4,Cordova> = 8.0.0,Ionic-CLI> = 5.1,cordova-ios> = 5.1.0
- 这些依赖项中的每一个都有可用于命令行构建的修补程序,并且 pod 依赖项解析可以正常工作
- 您必须使用 @ capacitor / ios> = 1.4.0。该版本之前的版本未将 OpenURL 通知与其他插件(包括 Branch)联合。
use_frameworks
has been removed from this plugin and will now be statically built. If the another podfile usesuse_frameworks
that is fine but this plugin no longer flags itself as dynamic. Ideally your app should be updated to removeuse_frameworks!
from your Podfile.- When using Capacitor, you must add the following entries yourself to
ios/App/App/Info.plist
:
<key>CFBundleURLTypes</key>
<array>
<dict>
<key>CFBundleURLName</key>
<string>com.getcapacitor.capacitor</string>
<key>CFBundleURLSchemes</key>
<array>
<string>capacitor</string>
</array>
</dict>
<dict>
<key>CFBundleURLName</key>
<string>branch-cordova-sdk</string>
<key>CFBundleURLSchemes</key>
<array>
<string>[YOUR URL SCHEME HERE]</string>
</array>
</dict>
</array>
<key>branch_key</key>
<string>[YOUR BRANCH LIVE KEY]</string>
<key>branch_app_domain</key>
<string>[YOUR DOMAIN].app.link</string>
- 这是 Capacitor 的一个局限,其中显式配置更改是开发人员的责任,以避免 “magic config”
- 使用 Capacitor 时,您必须自己通过 Xcode entitlement 编辑器添加 Associated Domain 权限
- 这必须使用 Xcode 完成—这是 Capacitor 核心理念的一部分,您可以控制每个配置文件的更改
- 在 Xcode 中打开 "Signing & Entitlements" 选项卡,添加 Associated Domains entitlement,并添加在 Branch dashboard 上找到的 URL。
AppStore:iOS
- 应用被拒绝,因为它使用推送通知功能,但未声明 aps-environment key
- 当 branch-cordova-sdk 转为使用 CocoaPods 时,Cordova 9 中进行了更改,其中单独的授权文件不再放在一起。通过将 Branch 配置直接添加到您现有的权利中,而不是创建新的权利文件,此插件的版本4.1.0中已解决此问题。此更改与 Cordova 8 向后兼容。
Apple Search Ads:iOS
- Follow the native iOS documentation for setting up Apple Search Ads
Updated 4 months ago