使用 DesktopManger 备份/恢复 net.rim.device.api.util.Persitable 对象
任务是使用 BB Desktop Manager 或任何其他方式备份/恢复 Persistable 对象。主要目的是在设备固件更新之间保留数据...
我有:
public final class UserList implements Persistable {
//The persistable objects.
private Hashtable fData;
//Initialize the class with empty values.
public UserList() {
fData = new Hashtable();
}
//Initialize the class with the specified values.
public UserList(Hashtable p) {
fData = p;
}
public Hashtable getData() {
return fData;
}}
我还实现了 SyncItem(如示例之一中所示)
public final class UserListSync extends SyncItem {
private static UserList fList;
private static final int FIELDTAG_NAME = 1;
private static final int FIELDTAG_AGE = 2;
private static PersistentObject store;
static {
store = PersistentStore.getPersistentObject(0x3167239af4aa40fL);
}
public UserListSync() {
}
public String getSyncName() {
return "Sync Item Sample";
}
public String getSyncName(Locale locale) {
return null;
}
public int getSyncVersion() {
return 1;
}
public boolean getSyncData(DataBuffer db, int version) {
boolean retVal = true;
synchronized (store) {
if (store.getContents() != null) {
fList = (UserList)store.getContents();
}
}
try {
Enumeration e = fList.getData().keys();
while (e.hasMoreElements()) {
String key = (String) e.nextElement();
String value = (String) fList.getData().get(key);
//Write the name.
db.writeShort(key.length() + 1);
db.writeByte(FIELDTAG_NAME);
db.write(key.getBytes());
db.writeByte(0);
//Write the age.
db.writeShort(value.length() + 1);
db.writeByte(FIELDTAG_AGE);
db.write(value.getBytes());
db.writeByte(0);
}
} catch (Exception e) {
retVal = false;
}
return retVal;
}
//Interprets and stores the data sent from the Desktop Manager.
public boolean setSyncData(DataBuffer db, int version) {
int length;
Hashtable table = new Hashtable();
Vector keys = new Vector();
Vector values = new Vector();
boolean retVal = true;
try {
//Read until the end of the Databuffer.
while (db.available() > 0) {
//Read the length of the data.
length = db.readShort();
//Set the byte array to the length of the data.
byte[] bytes = new byte[length];
//Determine the type of data to be read (name or age).
switch (db.readByte()) {
case FIELDTAG_NAME:
db.readFully(bytes);
keys.addElement(new String(bytes).trim());
break;
case FIELDTAG_AGE:
db.readFully(bytes);
values.addElement(new String(bytes).trim());
break;
}
}
} catch (Exception e) {
retVal = false;
}
for (int i = 0; i < keys.size(); i++) {
table.put(keys.elementAt(i), values.elementAt(i));
}
try {
//Store the new data in the persistent store object.
fList = new UserList(table);
store.setContents(fList);
store.commit();
} catch (Exception e) {
retVal = false;
}
return retVal;
}}
入口点如下:
public class SyncItemSample extends UiApplication {
private static PersistentObject store;
private static UserList userList;
static {
store = PersistentStore.getPersistentObject(0x3167239af4aa40fL);
}
public static void main(String[] args) {
SyncItemSample app = new SyncItemSample();
app.enterEventDispatcher();
}
public SyncItemSample() {
UserListScreen userListScreen;
//Check to see if the store exists on the BlackBerry.
synchronized (store) {
if (store.getContents() == null) {
//Store does not exist, create it with default values
userList = new UserList();
store.setContents(userList);
store.commit();
} else {
//Store exists, retrieve data from store.
userList = (UserList)store.getContents();
}
}
//Create and push the UserListScreen.
userListScreen = new UserListScreen(userList);
pushScreen(userListScreen);
}}
这是屏幕的实现:
public final class UserListScreen extends MainScreen {
Vector fLabels = new Vector();
Vector fValues = new Vector();
VerticalFieldManager leftColumn = new VerticalFieldManager();
VerticalFieldManager rightColumn = new VerticalFieldManager();
UserList fList;
public UserListScreen(UserList list) {
super();
fList = list;
//Create a horizontal field manager to hold the two vertical field
//managers to display the names and ages in two columns.
VerticalFieldManager inputManager = new VerticalFieldManager();
HorizontalFieldManager backGround = new HorizontalFieldManager();
//Array of fields to display the names and ages.
LabelField title = new LabelField("User List",
LabelField.ELLIPSIS | LabelField.USE_ALL_WIDTH);
setTitle(title);
final TextField fld1 = new TextField(TextField.NO_NEWLINE);
fld1.setLabel("input label");
inputManager.add(fld1);
final TextField fld2 = new TextField(TextField.NO_NEWLINE);
fld2.setLabel("input value");
inputManager.add(fld2);
final ButtonField fld3 = new ButtonField();
fld3.setChangeListener(new FieldChangeListener() {
public void fieldChanged(Field field, int context) {
fList.getData().put(fld1.getText().trim(), fld2.getText().trim());
refresh();
}
});
fld3.setLabel("add");
inputManager.add(fld3);
add(inputManager);
//Add the column titles and a blank field to create a space.
LabelField leftTitle = new LabelField("label ");
leftColumn.add(leftTitle);
LabelField rightTitle = new LabelField("value");
rightColumn.add(rightTitle);
refresh();
//Add the two vertical columns to the horizontal field manager.
backGround.add(leftColumn);
backGround.add(rightColumn);
//Add the horizontal field manager to the screen.
add(backGround);
}
private void refresh() {
leftColumn.deleteAll();
rightColumn.deleteAll();
fLabels.removeAllElements();
fValues.removeAllElements();
//Populate and add the name and age fields.
Enumeration e = fList.getData().keys();
while (e.hasMoreElements()) {
String key = (String) e.nextElement();
String value = (String) fList.getData().get(key);
final LabelField tmp1 = new LabelField(key);
final LabelField tmp2 = new LabelField(value);
leftColumn.add(tmp1);
rightColumn.add(tmp2);
fLabels.addElement(tmp1);
fValues.addElement(tmp2);
}
}
public boolean onClose() {
System.exit(0);
return true;
}}
所以如您所见应该很容易...
所以我运行所有这些应用程序,将值添加到持久对象,并且它们被正确添加,在设备重置期间存储等等... 当我运行桌面管理器并进行备份时,似乎 UserList 已备份,因为备份大小随着将新数据添加到持久存储中而增加。
但是,当我在 BB 9300 上运行“擦除设备”(并且持久存储中的所有数据都按预期被清除),然后从刚刚制作的备份文件运行恢复时,应用程序中没有任何内容更新,并且持久存储似乎是空的。
在一些示例中,我发现添加了备用入口点“init”,但我无法像 EclipsePlugin 中描述的那样调整所有内容,
您能否建议我如何在备份文件中存储数据以及如何从备份中检索相同的数据并加载它返回到应用程序,或者如何使用桌面管理器记录任何事件?
The task is to backup/restore Persistable object with BB Desktop Manager or in any other way. The main aim is to keep data between device firmware updates...
I have:
public final class UserList implements Persistable {
//The persistable objects.
private Hashtable fData;
//Initialize the class with empty values.
public UserList() {
fData = new Hashtable();
}
//Initialize the class with the specified values.
public UserList(Hashtable p) {
fData = p;
}
public Hashtable getData() {
return fData;
}}
I also have implemented SyncItem (as found in one of the examples)
public final class UserListSync extends SyncItem {
private static UserList fList;
private static final int FIELDTAG_NAME = 1;
private static final int FIELDTAG_AGE = 2;
private static PersistentObject store;
static {
store = PersistentStore.getPersistentObject(0x3167239af4aa40fL);
}
public UserListSync() {
}
public String getSyncName() {
return "Sync Item Sample";
}
public String getSyncName(Locale locale) {
return null;
}
public int getSyncVersion() {
return 1;
}
public boolean getSyncData(DataBuffer db, int version) {
boolean retVal = true;
synchronized (store) {
if (store.getContents() != null) {
fList = (UserList)store.getContents();
}
}
try {
Enumeration e = fList.getData().keys();
while (e.hasMoreElements()) {
String key = (String) e.nextElement();
String value = (String) fList.getData().get(key);
//Write the name.
db.writeShort(key.length() + 1);
db.writeByte(FIELDTAG_NAME);
db.write(key.getBytes());
db.writeByte(0);
//Write the age.
db.writeShort(value.length() + 1);
db.writeByte(FIELDTAG_AGE);
db.write(value.getBytes());
db.writeByte(0);
}
} catch (Exception e) {
retVal = false;
}
return retVal;
}
//Interprets and stores the data sent from the Desktop Manager.
public boolean setSyncData(DataBuffer db, int version) {
int length;
Hashtable table = new Hashtable();
Vector keys = new Vector();
Vector values = new Vector();
boolean retVal = true;
try {
//Read until the end of the Databuffer.
while (db.available() > 0) {
//Read the length of the data.
length = db.readShort();
//Set the byte array to the length of the data.
byte[] bytes = new byte[length];
//Determine the type of data to be read (name or age).
switch (db.readByte()) {
case FIELDTAG_NAME:
db.readFully(bytes);
keys.addElement(new String(bytes).trim());
break;
case FIELDTAG_AGE:
db.readFully(bytes);
values.addElement(new String(bytes).trim());
break;
}
}
} catch (Exception e) {
retVal = false;
}
for (int i = 0; i < keys.size(); i++) {
table.put(keys.elementAt(i), values.elementAt(i));
}
try {
//Store the new data in the persistent store object.
fList = new UserList(table);
store.setContents(fList);
store.commit();
} catch (Exception e) {
retVal = false;
}
return retVal;
}}
The entry poing is following:
public class SyncItemSample extends UiApplication {
private static PersistentObject store;
private static UserList userList;
static {
store = PersistentStore.getPersistentObject(0x3167239af4aa40fL);
}
public static void main(String[] args) {
SyncItemSample app = new SyncItemSample();
app.enterEventDispatcher();
}
public SyncItemSample() {
UserListScreen userListScreen;
//Check to see if the store exists on the BlackBerry.
synchronized (store) {
if (store.getContents() == null) {
//Store does not exist, create it with default values
userList = new UserList();
store.setContents(userList);
store.commit();
} else {
//Store exists, retrieve data from store.
userList = (UserList)store.getContents();
}
}
//Create and push the UserListScreen.
userListScreen = new UserListScreen(userList);
pushScreen(userListScreen);
}}
And here is an implementation of screen:
public final class UserListScreen extends MainScreen {
Vector fLabels = new Vector();
Vector fValues = new Vector();
VerticalFieldManager leftColumn = new VerticalFieldManager();
VerticalFieldManager rightColumn = new VerticalFieldManager();
UserList fList;
public UserListScreen(UserList list) {
super();
fList = list;
//Create a horizontal field manager to hold the two vertical field
//managers to display the names and ages in two columns.
VerticalFieldManager inputManager = new VerticalFieldManager();
HorizontalFieldManager backGround = new HorizontalFieldManager();
//Array of fields to display the names and ages.
LabelField title = new LabelField("User List",
LabelField.ELLIPSIS | LabelField.USE_ALL_WIDTH);
setTitle(title);
final TextField fld1 = new TextField(TextField.NO_NEWLINE);
fld1.setLabel("input label");
inputManager.add(fld1);
final TextField fld2 = new TextField(TextField.NO_NEWLINE);
fld2.setLabel("input value");
inputManager.add(fld2);
final ButtonField fld3 = new ButtonField();
fld3.setChangeListener(new FieldChangeListener() {
public void fieldChanged(Field field, int context) {
fList.getData().put(fld1.getText().trim(), fld2.getText().trim());
refresh();
}
});
fld3.setLabel("add");
inputManager.add(fld3);
add(inputManager);
//Add the column titles and a blank field to create a space.
LabelField leftTitle = new LabelField("label ");
leftColumn.add(leftTitle);
LabelField rightTitle = new LabelField("value");
rightColumn.add(rightTitle);
refresh();
//Add the two vertical columns to the horizontal field manager.
backGround.add(leftColumn);
backGround.add(rightColumn);
//Add the horizontal field manager to the screen.
add(backGround);
}
private void refresh() {
leftColumn.deleteAll();
rightColumn.deleteAll();
fLabels.removeAllElements();
fValues.removeAllElements();
//Populate and add the name and age fields.
Enumeration e = fList.getData().keys();
while (e.hasMoreElements()) {
String key = (String) e.nextElement();
String value = (String) fList.getData().get(key);
final LabelField tmp1 = new LabelField(key);
final LabelField tmp2 = new LabelField(value);
leftColumn.add(tmp1);
rightColumn.add(tmp2);
fLabels.addElement(tmp1);
fValues.addElement(tmp2);
}
}
public boolean onClose() {
System.exit(0);
return true;
}}
So as you see it should be very easy...
So all of these I run application, add values to Persistent object and they are added correctly, are stored during device resets and so on...
When I run Desktop Manager and make a Backup it seems that UserList is backed-up, as size of backup grows together with adding new data into persistent store.
But when I run "Wipe device" on my BB 9300 (and all data from Persistent store is cleared as it is expected) and then run Restore from just made backup file - nothing is updated in the Application and persistent store is seems to be empty.
In some examples I have found adding alternate entry point "init" but I can't tune eveything like it is described with my EclipsePlugin
Could you advice me how to store data in backup file and the to retrieve the same data from backup and load it back to the application, or how to log any of events with Desktop Manager?
如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。
绑定邮箱获取回复消息
由于您还没有绑定你的真实邮箱,如果其他用户或者作者回复了您的评论,将不能在第一时间通知您!
发布评论
评论(1)
如果有人遇到过同样的问题,您可以尝试在擦除设备之前断开设备的连接。这很奇怪,但有帮助:)
If someone has experienced the same problem you can try to disconnect the device before wiping it. It is strange but it helped :)