-
Notifications
You must be signed in to change notification settings - Fork 49
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Use xmlpull-style parser and serialiser #18
Comments
I really appreciate and you are welcome do this.
I tried to implement exactly this, Here are my reasons not to use the standard XmlPullParser.
We can't separate XML and android but I can't see any good reason converting to/from readable XML, we have the power to do any editing live. |
When I proposed the use of xmlpull, I didn't say that I'd use it to parse raw XML files. I was only implying that the binary XML parser (i.e. For raw XML files, I don't see any reason to package the |
Sorry i misunderstood you, you are right it make sense for bin XML to have standard serializer. A developer have to go thru all lines of ResXmlDocument code to understand what it does. It is easy to implement XmlPullParser on ResXmlDocument.
if it is on your public repo please share me the link Now everything on arsc side becoming stable and now i have a chance to fully concentrate on XML |
I haven't yet pushed it.
Precisely. Working with ResXmlDocument is not very straight-forward and requires some documentation in order to make sense of the API. I would always closely follow Android because the developers are expected to already familiar with Android ecosystem. |
Check ResXmlPullParser |
Almost perfect! This is my initial review:
|
On which method ?
For what purpose ?
Will do on next commit |
The default
For resolving references. With this implementation, a nasty workaround is required to do this. Example: public static String getAttributeName(@NonNull ResXmlPullParser parser, @NonNull EntryStore entryStore, int index) {
int resourceId = parser.getAttributeNameResource(index);
String name;
if (resourceId == 0) {
name = parser.getAttributeName(index);
} else {
EntryGroup group = entryStore.getEntryGroup(resourceId);
if (group == null) {
name = String.format("@0x%08x", resourceId);
} else {
name = group.getSpecName();
}
}
return name;
}
public static String getAttributeValue(@NonNull ResXmlPullParser parser, @NonNull EntryStore entryStore, int currentPackageId, int index) {
int resourceId = parser.getAttributeNameResource(index);
// Use Reflection to fetch ResXmlAttribute to resolve references
ResXmlAttribute attr = null;
try {
Method getResXmlAttributeAt = ResXmlPullParser.class.getDeclaredMethod("geResXmlAttributeAt", int.class);
getResXmlAttributeAt.setAccessible(true);
attr = (ResXmlAttribute) getResXmlAttributeAt.invoke(parser, index);
} catch (Throwable th) {
th.printStackTrace();
}
if (attr == null) {
return parser.getAttributeValue(index);
}
ValueType valueType = attr.getValueType();
int raw = attr.getData();
String value;
if (valueType == ValueType.STRING) {
value = ValueDecoder.escapeSpecialCharacter(attr.getValueAsString());
} else {
value = ValueDecoder.decode(entryStore,
currentPackageId,
resourceId,
valueType,
raw);
}
return value;
} |
If you loaded your bin xml from ApkModule, we can retrieve all decoding materials
I didn't test this on android os, I appreciate if you share me your test result |
Sorry, I don't know what values are you looking for. But this is precisely what is needed, I think.
I understand that. But it has use-case when a dev is working with
I'm exclusively testing the library on Android. So, it's working as expected. |
I have done a bit more analysis on this, and I think you should make |
Convincing
I will do on next push, but i don't like Since you are testing on android os, can you test class loader is using class public interface XmlPullParser{
public static void checkThisClassUsed(){
throw new RuntimeException("This class is used");
}
Then call method |
It uses the framework implementation as expected. Point 3 from the comment above is not yet implemented, it appears. It still does not return namespace attributes. |
Here I tried to implement I didn't check the exact implementation of AOSP, I just assumed:
|
Your assumptions are almost correct. As per |
Here I tried strict implementation of XMLPULL. I am not sure I got it |
@MuntashirAkon |
Thanks! I am actually quite busy rewriting some logic in my app (also had an accident two weeks ago), so haven't got the time reply to your last message. I'll surely test them all and reply as soon as I'm back on track. |
It appears my tests are failing because both unknown reference markers, namely
All APK editing software use those conventional markers. So, it would be very confusing to the users if we use something different. |
The reason I changed to |
Two observations:
|
Decoding to XML is intended to un - obfuscated or lightly obfuscated resources, the dev is responsible to correct all obfuscation on binary resources or use
My intention at the beginning was just for attribute names but I lost it somewhere.
|
What I wrote above were only suggestions. You should be the one to decide how you would set standards, not us. But whatever you do, you should also take the conventional usage in mind and note down those that aren't so that we can also pass that to our users. I think you should really think about making the output stable, that is, regardless of the changes in the API, the output should be consistent. And to do that, you should think about how cases like this would be taken care of before you do anything else. This way, developers like me can make the best use of this library without constantly thinking about the output representation each time an update is made. Changes in output representation also has other side-effects in real life. Suppose, a user has stored the output XML and wants to convert it into AXML later on but only to realise that it won't work because the parser can no longer parse the XML file properly. Now, I think attribute names should be small and consistent. The attribute name documentation only suggest a handful of usable ASCII characters. So, if you're really looking to develop some meaningful standards for attribute names, here's what I think is more practical and android-way to solve this issue: Use the |
Thank you for brief suggestion !
Characters
Name can not start with digits Keep in mind that namespace is not available on some cases like values of |
As per the the docs, the actual name is |
Prefix doesn't count as a part of attribute name, unless you mod parser (I did this when we had used MXParser). Check it again |
You're right. XML validator seems to complain when
|
Nice suggestions , I will try with |
All tests are passing again. Thank you so much! I'll test out the serialiser more thoroughly and report back. |
This is just what I've felt while using the library and only my expert opinion. I can also help you implementing this if you choose to do this.
The use of
xmlpull
-style parser and serialiser is quite common in Android ecosystem. The framework itself uses this library for parsing both normal and binary XML (newly introduced in Android 12) files. So, it allows greater control such as easy to convert between one XML format to another by simultaneous use of parser and serialiser. This also make it easier to separate reading and writing the XML contents. So, I propose, possibly, creating a wrapper around theXMLDocument
class.The text was updated successfully, but these errors were encountered: