Many and various fixes for XML and URL stuff

git-svn-id: svn+ssh://svn.gna.org/svn/gnustep/libs/base/trunk@7587 72102866-910b-0410-8b05-ffd578937521
This commit is contained in:
Richard Frith-MacDonald 2000-09-22 18:55:21 +00:00
parent 2458682e57
commit 791b91afdd
11 changed files with 167 additions and 98 deletions

View file

@ -8,9 +8,16 @@
tolerate URLs where the network part is missing and the '//' left out.
* Source/GSXML.m: Reorganized init methods in line with
Manuels ideas but with naming consistent with other classes.
Correct methods for setting parser behavior for the object concerned
rather than default behavior for all parsers.
Support NSURL parsing.
* Source/propList.h: Update for change in GSXMLParser API.
* Documentation/gsdoc/GSXMLParser.gsdoc: update for new initialisation
methods.
* Source/NSArray.m: Put code in place to generate XML proplists
* Source/NSDictionary.m: Put code in place to generate XML proplists
* Source/GSCompatibility.m: Put code in place to generate XML proplists
but disable it until working entity replacement is done.
2000-09-21 Adam Fedor <fedor@gnu.org>

View file

@ -182,7 +182,7 @@
</p>
<p>
The source for the parsing process is not specified - so
parsing must be done incfrementally by feeding data to the
parsing must be done incrementally by feeding data to the
parser.
</p>
</desc>
@ -236,9 +236,8 @@
</p>
<p>
Sets the input source for the parser to be the specified data
object (which must contain a nul terminated XML document),
so parsing of the entire document will be performed rather than
incremental parsing.
object (which must contain an XML document), so parsing of the
entire document will be performed rather than incremental parsing.
</p>
</desc>
</method>
@ -254,7 +253,8 @@
<method type="GSXMLDocument*">
<sel>doc</sel>
<desc>
<p>Return GSXMLDocument object.
<p>
Return GSXMLDocument object.
</p>
</desc>
</method>
@ -264,7 +264,7 @@
<desc>
<p>
Parse source. Return YES if parsed, otherwise NO.
This method should be called once to parse the entiore document.
This method should be called once to parse the entire document.
</p>
<example>
GSXMLParser *p = [GSXMLParser parserWithContentsOfFile:@"macos.xml"];
@ -292,8 +292,8 @@
block of data from the same document. After the whole of the
document has been parsed, the method should be called with
an empty or nil data object to indicate end of parsing.
Once this has been done, the method may be used again to
parse a new document.
On this final call, the return value indicates whether the
document was valid or not.
</p>
<example>
GSXMLParser *p = [GSXMLParser parserWithSAXHandler: nil source: nil];
@ -307,7 +307,7 @@
}
// Do something with document parsed
[p parse: nil]; // Ready to parse another document.
[p parse: nil]; // Completed parsing of document.
</example>
</desc>
@ -318,7 +318,7 @@
<arg type="BOOL">yesno</arg>
<desc>
<p>
Set and return the previous value for default entity support.
Set and return the previous value for entity support.
Initially the parser always keeps entity references instead
of substituting entity values in the output.
</p>
@ -330,8 +330,7 @@
<arg type="BOOL">yesno</arg>
<desc>
<p>
Set and return the previous value for default blanks
text nodes support.
Set and return the previous value for blank text nodes support.
ignorableWhitespace() are only generated when running
the parser in validating mode and when the current element
doesn't allow CDATA or mixed content.

View file

@ -226,7 +226,7 @@ Creation of a new Parser by calling
<p>
The source for the parsing process is not specified - so
parsing must be done incfrementally by feeding data to the
parsing must be done incrementally by feeding data to the
parser.
</p>
@ -280,9 +280,8 @@ Creation of a new Parser by calling
<p>
Sets the input source for the parser to be the specified data
object (which must contain a nul terminated XML document),
so parsing of the entire document will be performed rather than
incremental parsing.
object (which must contain an XML document), so parsing of the
entire document will be performed rather than incremental parsing.
</p>
@ -300,7 +299,8 @@ Return pointer to xmlParserCtxt structure.
- (GSXMLDocument*) <b>doc</b>;<br>
<p>
Return GSXMLDocument object.
Return GSXMLDocument object.
</p>
@ -311,7 +311,7 @@ Return GSXMLDocument object.
<p>
Parse source. Return YES if parsed, otherwise NO.
This method should be called once to parse the entiore document.
This method should be called once to parse the entire document.
</p>
<a name ="label-18">example </a>
@ -343,8 +343,8 @@ Return GSXMLDocument object.
block of data from the same document. After the whole of the
document has been parsed, the method should be called with
an empty or nil data object to indicate end of parsing.
Once this has been done, the method may be used again to
parse a new document.
On this final call, the return value indicates whether the
document was valid or not.
</p>
<a name ="label-20">example </a>
@ -361,7 +361,7 @@ Return GSXMLDocument object.
}
// Do something with document parsed
[p parse: nil]; // Ready to parse another document.
[p parse: nil]; // Completed parsing of document.
</pre>
@ -373,7 +373,7 @@ Return GSXMLDocument object.
<p>
Set and return the previous value for default entity support.
Set and return the previous value for entity support.
Initially the parser always keeps entity references instead
of substituting entity values in the output.
</p>
@ -385,8 +385,7 @@ Return GSXMLDocument object.
<p>
Set and return the previous value for default blanks
text nodes support.
Set and return the previous value for blank text nodes support.
ignorableWhitespace() are only generated when running
the parser in validating mode and when the current element
doesn't allow CDATA or mixed content.

View file

@ -51,16 +51,20 @@
<h3><a name ="method-0">URLWithString:</a></h3>
+ (id) <b>URLWithString:</b> (NSString*)URLString;<br>
Initializes with a string as specified in RFCs 1738 and 1808
<hr>
<h3><a name ="method-1">URLWithString:relativeToURL:</a></h3>
+ (id) <b>URLWithString:</b> (NSString*)URLString <b>relativeToURL:</b> (NSURL*)baseURL;<br>
Initializes relative to a base URL, with a string as
specified in RFCs 1738 and 1808
<hr>
<h3><a name ="method-2">fileURLWithPath:</a></h3>
+ (id) <b>fileURLWithPath:</b> (NSString*)path;<br>
Initializes as a file schem URL with the specified path.
<hr>
<hr><h2>Instances Methods </h2>

View file

@ -52,21 +52,27 @@
<h3><a name ="method-0">URLHandleClassForURL:</a></h3>
+ (Class) <b>URLHandleClassForURL:</b> (NSURL*)anURL;<br>
Returns the most recently registered NSURLHandle subclass that
responds to <code>canInitWithURL:</code> with <code>YES</code>
<hr>
<h3><a name ="method-1">cachedHandleForURL:</a></h3>
+ (NSURLHandle*) <b>cachedHandleForURL:</b> (NSURL*)anURL;<br>
Returns a previously created object that handles the specified
URL (if any exists).
<hr>
<h3><a name ="method-2">canInitWithURL:</a></h3>
+ (BOOL) <b>canInitWithURL:</b> (NSURL*)anURL;<br>
Implemented by subclasses to say which URLs they can handle.
<hr>
<h3><a name ="method-3">registerURLHandleClass:</a></h3>
+ (void) <b>registerURLHandleClass:</b> (Class)anURLHandleSubclass;<br>
Used to register a subclass as being available to handle URLs.
<hr>
<hr><h2>Instances Methods </h2>

View file

@ -109,6 +109,8 @@ BOOL GSMacOSXCompatibleGeometry()
BOOL GSMacOSXCompatiblePropertyLists()
{
/* HACK until xml propertylists fully working */
return NO;
if (setupDone == NO)
compatibilitySetup();
return MacOSXCompatiblePropertyLists;
@ -178,9 +180,30 @@ XMLString(NSString* obj)
return obj;
}
static NSString *indentStrings[] = {
@"",
@" ",
@"\t",
@"\t ",
@"\t\t",
@"\t\t ",
@"\t\t\t",
@"\t\t\t ",
@"\t\t\t\t",
@"\t\t\t\t ",
@"\t\t\t\t\t",
@"\t\t\t\t\t ",
@"\t\t\t\t\t\t"
};
static void
XMLPlObject(NSMutableString *dest, id obj)
XMLPlObject(NSMutableString *dest, id obj, NSDictionary *loc, unsigned lev)
{
if (lev >= sizeof(indentStrings) / sizeof(*indentStrings))
lev = sizeof(indentStrings) / sizeof(*indentStrings) - 1;
[dest appendString: indentStrings[lev]];
if ([obj isKindOfClass: [NSString class]])
{
[dest appendString: @"<string>"];
@ -233,14 +256,19 @@ XMLPlObject(NSMutableString *dest, id obj)
e = [obj objectEnumerator];
while ((obj = [e nextObject]))
{
XMLPlObject(dest, obj);
XMLPlObject(dest, obj, loc, lev + 1);
}
[dest appendString: indentStrings[lev]];
[dest appendString: @"</array>\n"];
}
else if ([obj isKindOfClass: [NSDictionary class]])
{
NSEnumerator *e;
id key;
unsigned nxt = lev + 1;
if (lev >= sizeof(indentStrings) / sizeof(*indentStrings))
lev = sizeof(indentStrings) / sizeof(*indentStrings) - 1;
[dest appendString: @"<dict>\n"];
e = [obj keyEnumerator];
@ -249,11 +277,13 @@ XMLPlObject(NSMutableString *dest, id obj)
id val;
val = [obj objectForKey: key];
[dest appendString: indentStrings[nxt]];
[dest appendString: @"<key>"];
[dest appendString: XMLString(key)];
[dest appendString: @"</key>\n"];
XMLPlObject(dest, val);
XMLPlObject(dest, val, loc, nxt);
}
[dest appendString: indentStrings[lev]];
[dest appendString: @"</dict>\n"];
}
else
@ -265,3 +295,18 @@ XMLPlObject(NSMutableString *dest, id obj)
}
}
NSString*
GSXMLPlMake(id obj, NSDictionary *loc, unsigned lev)
{
NSMutableString *dest;
dest = [NSMutableString stringWithCString:
"<?xml version=\"1.0\" encoding=\"UTF-8\"?>\n<!DOCTYPE plist "
"SYSTEM \"file://localhost/System/Library/DTDs/PropertyList.dtd\">\n"
"<plist version=\"0.9\">\n"];
XMLPlObject(dest, obj, loc, 0);
[dest appendString: @"</plist>"];
return dest;
}

View file

@ -32,6 +32,8 @@
#include <Foundation/GSXML.h>
#include <Foundation/NSData.h>
#include <Foundation/NSValue.h>
#include <Foundation/NSURL.h>
#include <Foundation/NSMapTable.h>
#include <Foundation/NSException.h>
#include <Foundation/NSFileManager.h>
@ -937,10 +939,14 @@ static NSString *endMarker = @"At end of incremental parse";
RELEASE(self);
return nil;
}
self = [self init];
if (self != nil)
saxHandler = RETAIN(handler);
[saxHandler parser: self];
lib = (void*)xmlCreatePushParserCtxt([saxHandler lib], saxHandler, 0, 0, "");
if (lib == NULL)
{
saxHandler = RETAIN(handler);
NSLog(@"Failed to create libxml parser context");
RELEASE(self);
return nil;
}
return self;
}
@ -1013,29 +1019,28 @@ static NSString *endMarker = @"At end of incremental parse";
if ([src isKindOfClass: [NSData class]])
{
lib = (void*)xmlCreateMemoryParserCtxt((void*)[src bytes],
[src length]-1);
if (lib == NULL)
{
NSLog(@"out of memory");
return NO;
}
}
else if ([src isKindOfClass: NSString_class])
{
NSFileManager *mgr = [NSFileManager defaultManager];
NSData *data = [NSData dataWithContentsOfFile: src];
if ([mgr isReadableFileAtPath: src] == NO)
if (data == nil)
{
NSLog(@"File to parse (%@) is not readable", src);
return NO;
}
lib = (void*)xmlCreateFileParserCtxt([src cString]);
if (lib == NULL)
{
NSLog(@"out of memory");
ASSIGN(src, data);
}
else if ([src isKindOfClass: [NSURL class]])
{
NSData *data = [src resourceDataUsingCache: YES];
if (data == nil)
{
NSLog(@"URL to parse (%@) is not readable", src);
return NO;
}
}
ASSIGN(src, data);
}
else
{
@ -1043,18 +1048,10 @@ static NSString *endMarker = @"At end of incremental parse";
return NO;
}
if (saxHandler != nil)
{
NSAssert([saxHandler parser] == nil, NSGenericException);
free(((xmlParserCtxtPtr)lib)->sax);
((xmlParserCtxtPtr)lib)->sax = [saxHandler lib];
((xmlParserCtxtPtr)lib)->userData = saxHandler;
[saxHandler parser: self];
}
tmp = RETAIN(src);
ASSIGN(src, endMarker);
xmlParseDocument(lib);
xmlParseChunk(lib, [tmp bytes], [tmp length], 0);
xmlParseChunk(lib, 0, 0, 0);
RELEASE(tmp);
if (((xmlParserCtxtPtr)lib)->wellFormed)
@ -1065,17 +1062,11 @@ static NSString *endMarker = @"At end of incremental parse";
- (BOOL) parse: (NSData*)data
{
/*
* Permit start of new parse after completed one.
*/
if (src == endMarker)
{
xmlFreeDoc(((xmlParserCtxtPtr)lib)->myDoc);
xmlClearParserCtxt(lib);
lib = NULL;
src = nil;
NSLog(@"GSXMLParser -parse: called on object that is fully parsed");
return NO;
}
if (src != nil)
{
NSLog(@"XMLParser -parse: called for parser not initialised with nil");
@ -1104,21 +1095,7 @@ static NSString *endMarker = @"At end of incremental parse";
}
else
{
if (lib == NULL)
{
NSAssert([saxHandler parser] == nil, NSGenericException);
[saxHandler parser: self];
lib = (void*)xmlCreatePushParserCtxt([saxHandler lib], saxHandler,
[data bytes], [data length], "incremental");
if (lib == NULL)
{
return NO;
}
}
else
{
xmlParseChunk(lib, [data bytes], [data length], 0);
}
xmlParseChunk(lib, [data bytes], [data length], 0);
return YES;
}
}
@ -1143,17 +1120,26 @@ static NSString *endMarker = @"At end of incremental parse";
- (BOOL) substituteEntities: (BOOL)yesno
{
return xmlSubstituteEntitiesDefault(yesno);
BOOL result = ((xmlParserCtxtPtr)lib)->replaceEntities ? YES : NO;
((xmlParserCtxtPtr)lib)->replaceEntities = (yesno == YES) ? 1 : 0;
return result;
}
- (BOOL) keepBlanks: (BOOL)yesno
{
return xmlKeepBlanksDefault(yesno);
BOOL result = ((xmlParserCtxtPtr)lib)->keepBlanks ? YES : NO;
((xmlParserCtxtPtr)lib)->keepBlanks = (yesno == YES) ? 1 : 0;
return result;
}
- (BOOL) doValidityChecking: (BOOL)yesno
{
return !(xmlDoValidityCheckingDefaultValue = yesno);
BOOL result = ((xmlParserCtxtPtr)lib)->validate ? YES : NO;
((xmlParserCtxtPtr)lib)->validate = (yesno == YES) ? 1 : 0;
return result;
}
- (BOOL) getWarnings: (BOOL)yesno
@ -1161,7 +1147,6 @@ static NSString *endMarker = @"At end of incremental parse";
return !(xmlGetWarningsDefaultValue = yesno);
}
- (void) setExternalEntityLoader: (void*)function
{
xmlSetExternalEntityLoader((xmlExternalEntityLoader)function);

View file

@ -656,14 +656,25 @@ static SEL rlSel = @selector(removeLastObject);
- (NSString*) descriptionWithLocale: (NSDictionary*)locale
indent: (unsigned int)level
{
NSMutableString *result;
extern BOOL GSMacOSXCompatiblePropertyLists();
result = [[NSGMutableCString alloc] initWithCapacity: 20*[self count]];
result = AUTORELEASE(result);
[self descriptionWithLocale: locale
indent: level
to: (id<GNUDescriptionDestination>)result];
return result;
if (GSMacOSXCompatiblePropertyLists() == YES)
{
extern NSString *GSXMLPlMake(id obj, NSDictionary *loc, unsigned lev);
return GSXMLPlMake(self, locale, level);
}
else
{
NSMutableString *result;
result = [[NSGMutableCString alloc] initWithCapacity: 20*[self count]];
result = AUTORELEASE(result);
[self descriptionWithLocale: locale
indent: level
to: (id<GNUDescriptionDestination>)result];
return result;
}
}
static NSString *indentStrings[] = {

View file

@ -627,14 +627,25 @@ compareIt(id o1, id o2, void* context)
- (NSString*) descriptionWithLocale: (NSDictionary*)locale
indent: (unsigned int)level
{
NSMutableString *result;
extern BOOL GSMacOSXCompatiblePropertyLists();
result = AUTORELEASE([[NSGMutableCString alloc] initWithCapacity:
20*[self count]]);
[self descriptionWithLocale: locale
indent: level
to: (id<GNUDescriptionDestination>)result];
return result;
if (GSMacOSXCompatiblePropertyLists() == YES)
{
extern NSString *GSXMLPlMake(id obj, NSDictionary *loc, unsigned lev);
return GSXMLPlMake(self, locale, level);
}
else
{
NSMutableString *result;
result = AUTORELEASE([[NSGMutableCString alloc] initWithCapacity:
20*[self count]]);
[self descriptionWithLocale: locale
indent: level
to: (id<GNUDescriptionDestination>)result];
return result;
}
}
static NSString *indentStrings[] = {

View file

@ -725,12 +725,12 @@ static id parsePl(pldata* pld)
{
NSData *data;
GSXMLParser *parser;
char *buf = NSZoneMalloc(NSDefaultMallocZone(), pld->end+1);
char *buf = NSZoneMalloc(NSDefaultMallocZone(), pld->end);
memcpy(buf, pld->ptr, pld->end);
buf[pld->end] = '\0';
data = [NSData dataWithBytesNoCopy: buf length: pld->end+1];
data = [NSData dataWithBytesNoCopy: buf length: pld->end];
parser = [GSXMLParser parserWithData: data];
[parser substituteEntities: NO];
if ([parser parse] == YES)
{
if (![[[[parser doc] root] name] isEqualToString: @"plist"])

View file

@ -23,6 +23,8 @@ int main (int argc, char **argv)
NSData *data = [url resourceDataUsingCache: YES];
NSLog(@"%@", data);
url = [NSURL fileURLWithPath: @"/tmp/z"];
[url setResourceData: data];
NSLog(@"%@", _(Testing));
NSLog(@"%@", $(@"Testing"));